Объясните визуально теорему Пифагора


36

Общее визуальное объяснение теоремы Пифагора таково:

3 boxes

Квадраты предназначены для представления квадрата длины стороны и площадей a + b = c, как говорится в теореме Пифагора.

Эта часть - то, что вы должны показать.

Твое задание

  • В качестве входных данных вы получите два целых числа, предназначенных для представления сторон aи bпрямоугольного треугольника (например 3, 4).
  • Вы будете тогда делать квадраты из длин a, bи cиз #характера. Например вот 3:
###
###
###
  • Затем вы отформатируете их в математическое уравнение, которое объясняет конкретный пифагорейский триплет:
             #####
      ####   #####
###   ####   #####
###   ####   #####
### + #### = #####
  • Обратите внимание , как =и +знаки имеют пробелы с обеих сторон и как все находится на дне.
  • Вы никогда не получите значения для, aи bэто делает cнецелым.
  • Это поэтому выигрывает самый короткий код в байтах !

Тестовые случаи

(больше, когда у меня будет время, это действительно сложно сделать вручную)

3, 4
             #####
      ####   #####
###   ####   #####
###   ####   #####
### + #### = #####

6, 8
                    ##########
                    ##########
         ########   ##########
         ########   ##########
######   ########   ##########
######   ########   ##########
######   ########   ##########
######   ########   ##########
######   ########   ##########
###### + ######## = ##########

4, 3
             #####
####         #####
####   ###   #####
####   ###   #####
#### + ### = #####

5, 12
                       #############
        ############   #############
        ############   #############
        ############   #############
        ############   #############
        ############   #############
        ############   #############
        ############   #############
#####   ############   #############
#####   ############   #############
#####   ############   #############
#####   ############   #############
##### + ############ = #############

3
@bmarks "Вы никогда не получите значения для a и b, которые делают c нецелым."
Maltysen

2
@RetoKoradi хорошо области квадратов a+b=c
Maltysen

1
Если a, bи cопределяются как площади квадратов, то примеры некорректны.
Рето Коради

2
Вы должны добавить еще один хороший тестовый пример, например, 5 + 12 = 13.
mbomb007

7
Примечание: это не «визуальное объяснение теоремы Пифагора». Это теорема Пифагора. Первоначально он был сформулирован именно так: геометрически. Они даже не знали о квадратных корнях, что еще интереснее, сам Пифагор не верил в существование иррациональных чисел. Это означает, что Пифагор считал, что sqrt (2) может быть точно представлено делением двух конечных целых чисел. Первоначальная теорема - это то, что мы сейчас называем «визуальным представлением»
vsz

Ответы:



12

CJam, 49 байтов

" +   = "S/3/[q~_2$mh:H]_'#f*:a.*.\:+SH*f.e|zW%N*

Попробуйте онлайн в интерпретаторе CJam .

Как это работает

" +   = "S/3/ e# Split at spaces, the into chunks of length 3.
              e# This pushes [["" "+" ""] ["" "=" ""]].
[             e#
  q~          e# Read and interpret all input from STDIN.
  _2$         e# Copy both integers.
  mh          e# Calculate the hypotenuse of the triangle with those catheti.
  :H          e# Save the result in H.
]             e# Collect catheti and hypotenuse in an array.
_'#f*         e# Copy and replace each length with a string of that many hashes.
:a            e# Wrap each string in an array.
.*            e# Vectorized repetition. Turns strings into square arrays.
.\            e# Interleave with the string of operators.
:+            e# Concatenate to form an array of strings.
SH*           e# Push a string of spaces of length H.
f.e|          e# Mapped vectorized logical OR; pads all strings with spaces to
              e# length H.
zW%           e# Zip and reverse; rotates the array.
N*            e# Join the strings, separating by linefeeds.

11

Python 2, 134 100 байт

a,b=input()
i=c=int(abs(a+b*1j))
while i:print"# "[i>a]*a," +"[i<2],"# "[i>b]*b," ="[i<2],"#"*c;i-=1

Попробуйте онлайн.

Программа принимает входные данные в виде целых чисел, разделенных запятыми, вычисляет гипотенузу, используя встроенные комплексные числа Python, а затем возвращается к исходному значению этого значения, вычисляя и распечатывая каждую строку по мере поступления. Основной трюк в игре в гольф заключается в использовании индексации строк вместо условий для выбора# / +/ =vs пробел.

Изменить: Первая версия была жертвой серьезного чрезмерного проектирования - это и проще, и намного короче.


Я получил то же самое, потратив некоторое время, чтобы понять, что короче просто повторять "# "[i>a]*aвместо того, чтобы делать это для каждой переменной.
xnor

11

Юлия, 121 114 112 байт

f(a,b)=for i=1:(c=isqrt(a^2+b^2)) g(x,t)=(i>c-x?"#":" ")^x*(i<c?"  ":t)" ";println(g(a," +")g(b," =")g(c,""))end

Ungolfed:

function f(a,b)
    # Compute the hypotenuse length
    c = isqrt(a^2 + b^2)

    # Write the lines in a loop
    for i = 1:c
        # Make a function for constructing the blocks
        g(x,t) = (i <= c - x ? " " : "#")^x * (i < c ? "  " : t) " "

        println(g(a," +") g(b," =") g(c,""))
    end
end

Исправлена ​​проблема и сохранены 2 байта благодаря Glen O.


11

JavaScript ES6, 155 134 140 129 байт

(n,m)=>eval("for(o='',q=(b,s)=>' #'[z<b|0].repeat(b)+(z?'   ':s),z=i=Math.hypot(n,m);z--;)o+=q(n,' + ')+q(m,' = ')+q(i,'')+`\n`")

Я переписал это с for . Много игры в гольф все еще ...

Если что-то не работает, дайте мне знать. Я исправлю это утром.

Проверено на Safari Nightly

Ungolfed:

(n,m)=>
   Array(
     z=Math.hypot(n,m)
   ).fill()
   .map((l,i)=>
      (q=(j,s)=>
        (z-i<=j?'#':' ')
        .repeat(j)+
         (z-i-1?' ':s)
      )
      (n,`+`)+
      q(m,`=`)+
      q(z,'')
   ).join`
   `

Объяснение:

(Не обновлено), но все еще достаточно точно.

(n,m)=> // Function with two arguments n,m
   Array( // Create array of length...
    z=Math.hypot(n,m) // Get sqrt(n^2+m^2) and store in z
   ).fill() // Fill array so we can loop
   .map((l,i) => // Loop z times, take l, and i (index)
     (q=j=>( // Create function q with argument j
      z-i<=j? // If z-i is less than or equal to j...
        '#' // Use '#'
      : // OR
        ' ' // Use space
      ).repeat(j) // Repeat the character j times
     )(n) // Run with n
   + // Add to string
   ` ${ // Space
      (b=z-i-1)? // If this isn't the last line...
       ' ' // Return ' '
      : // Otherwise
       '+' // Plus
    } ${ // Space
      q(m) // run function q with arg m
    } ${ // Space
      b? // If b
       ' ' // Return space
      : // Otherwise
        '=' // '='
    }` + // Add to...
    '#'.repeat(z) // Repeat hashtag, z times
  ).join` // Join the new array with new lines
  `

DEMO

Версия ES5 Входные данные должны быть действительными наборами чисел :

function _taggedTemplateLiteral(e,t){return Object.freeze(Object.defineProperties(e,{raw:{value:Object.freeze(t)}}))}var _templateObject=_taggedTemplateLiteral(["\n"],["\n"]),t=function(e,t){return Array(z=Math.sqrt(e*e+t*t)).fill().map(function(r,n){return(q=function(e,t){return(z-n<=e?"#":" ").repeat(e)+(z-n-1?" ":t)})(e,"+")+q(t,"=")+q(z,"")}).join(_templateObject)};
// Demo
document.getElementById('go').onclick=function(){
  document.getElementById('output').innerHTML = t(+document.getElementById('input').value,
                                                 +document.getElementById('input2').value)
};
<div style="padding-left:5px;padding-right:5px;"><h2 style="font-family:sans-serif">Visually Explaining the Pythagorean Theorem</h2><div><div  style="background-color:#EFEFEF;border-radius:4px;padding:10px;"><input placeholder="Number 1" style="resize:none;border:1px solid #DDD;" id="input"><input placeholder="Number 2" style="resize:none;border:1px solid #DDD;" id="input2"><button id='go'>Run!</button></div><br><div style="background-color:#EFEFEF;border-radius:4px;padding:10px;"><span style="font-family:sans-serif;">Output:</span><br><pre id="output" style="background-color:#DEDEDE;padding:1em;border-radius:2px;overflow-x:auto;"></pre></div></div></div>


2
+1, но есть небольшая проблема, поскольку ОП говорит: «Обратите внимание, как знаки = и + имеют пробелы с обеих сторон и как все находится снизу».
Лео Лам

1
Фрагмент не работает в Firefox 40.0.3 (Windows 7x64 SP1).
Исмаэль Мигель

1
Фрагмент не работает в Chromium 44 Linux x64
Nenotlep

2
@IsmaelMiguel Эти последние случаи не нужно правильно обрабатывать, хотя: «Вы никогда не получите значения aи bчто делают cневстроенной.»
DLosc

2
+1 хорошее использование eval. Подсказка: (z<b?'#':' ')->' #'[z<b|0]
edc65

7

Pyth, 51 49 байт

AQJs.aQLj*b]*b\#;j_MCm_.[d\ Jcj[yJb\=byHb\+byG))b

Ожидает ввода в форме [3,4].

Попробуй здесь

AQ - назначает вход для G, H

Js.a,GH - рассчитывает гипотенузу как J

Lj*b]*b\#;- определяет y(b)как создание квадрата размера b(в другом месте кода bозначает перевод строки)

j_MCm_.[d\ Jcj[yJb\=byHb\+byG))b - Создает квадраты, площадки с пробелами и транспонирует

Сохранено два байта благодаря Maltysen.


Я не знаю точно, что делает ваш код, но я уверен, что он может выиграть от .interlace вместо всех этих списков.
Maltysen

@Maltysen К вашему последнему комментарию, на самом деле я не могу, потому что первое появление Jвнутри лямбда, которая оценивается после J первого использования.
Ypnypn

ах, не видел этого. Другое дело: *]можно заменитьm
Maltysen

3

Руби, 134

->a,b{c=((a**2+b**2)**0.5).round
c.times{|i|
d=i<c-1?'  ':'+='
puts (c-i>a ?' ':?#)*a+" #{d[0]}  #{(c-i>b ?' ':?#)*b} #{d[1]} "+?#*c}}

простой построчный подход.

Ниже в тестовой программе с символом, измененным на @, чтобы избежать путаницы с синтаксисом #{....}(«интерполяция строки»), используемым для вставки выражений в строку. Каждый вход должен быть указан в отдельной строке.

f=->a,b{c=((a**2+b**2)**0.5).round
c.times{|i|
d=i<c-1?'  ':'+='
puts (c-i>a ?' ':?@)*a+" #{d[0]}  #{(c-i>b ?' ':?@)*b} #{d[1]} "+?@*c}}

A=gets.to_i
B=gets.to_i
f.call(A,B)

Я не знаю Ruby, но я предполагаю, что это может стать короче, поскольку решения Ruby часто побеждают решения Python (по моему опыту). Для начала a*a+b*bследует вырезать два байта из вычисления c.
DLosc

3

C 176 байт

С не собирается выиграть это, но веселье того стоит.

#define A(x,y)for(j=x;j--;)putchar("# "[i+1>x]);printf(i?"   ":" "#y" ");
i;j;main(a,b,c){for(c=scanf("%d %d",&a,&b);a*a+b*b>c*c;c++);for(i=c;i--;puts("")){A(a,+)A(b,=)A(c,)}}

Довольно напечатано:

#define A(x,y)for(j=x;j--;)putchar("# "[i+1>x]);printf(i?"   ":" "#y" ");
i;j;
main(a,b,c)
{
    for(c=scanf("%d %d",&a,&b);a*a+b*b>c*c;c++);
    for(i=c;i--;puts(""))
    {
        A(a,+)
        A(b,=)
        A(c,)
    }
}

gcc позволяет нам передавать третий параметр в main (массив переменных среды), поэтому мы используем его для использования в наших целях.

The

for(c=scanf("%d %d",&a,&b);a*a+b*b>c*c++;);

будет эквивалентно

scanf("%d %d",&a,&b);
for(c=2;a*a+b*b>c*c++;);

потому что scanfвозвращает количество успешно отсканированных параметров.


2

PHP, 178 170 168 байт

Ввод GET параметров xи y. К сожалению, я не могу играть в гольф эти повторяющиеся струны.

<?php for(@$i=$z=hypot($x=$_GET[x],$y=$_GET[y]),@$s=str_repeat;$i;$i--)@print$s($i<=$x?~Ü:~ß,$x).(($l=$i==1)?~ßÔß:~ßßß).$s($i<=$y?~Ü:~ß,$y).($l?~ßÂß:~ßßß).$s(~Ü,$z).~õ;
  • Сохранено 8 байтов путем инвертирования всех моих строк и удаления кавычек.
  • Сохранено 2 байта путем замены условия $i>0на$i

Не знаю, почему PHP не нравится, @echoпоэтому пришлось пожертвовать 1 байтом @print.

В случае, если SE испортит кодировку, это должно быть закодировано в Windows-1252 (не UTF8).



Ah that makes sense. Thanks!
DankMemes

2

APL (Dyalog Extended), 33 29 bytesSBCS

-3 due to my extensions of Dyalog APL.

Anonymous prefix lambda:

{⊖⍕,' +=',⍪{⍵ ⍵⍴⍕#}¨⍵,√+/⍵*2}

Try it online!

{} "dfn"; is the argument (side lengths)

⍵*2 square

+/ sum

 square-root

⍵, prepend argument

{ apply the following anonymous lambda to each

  # root namespace

   format as text

  ⍵ ⍵⍴ use argument twice to reshape into matrix with those dimensions.

 make into column

' ++=', prepend these three characters to the three rows

, ravel (combine rows into list)

 format as text

 flip upside-down


1

CJam, 78 bytes

q~_2f#~+mQ+ee_2=~e>f{\~@1$-S*\'#*+_'#e=\a*_0=,S*@"+= "=1$,(S*\+1$a\a@a+++~}zN*

It first computes the hypotenuse (H), then, for each side (S), it builds an array of S lines made of: H-S spaces + S dashes. Finally, it transposes the matrix.

Demo


1

Lua5.2, 257 241 227 222 bytes

r=io.read
a=r"*n"b=r"*n"c=math.sqrt(a^2+b^2)d=a+b
w=io.write
for i=1,c do
for j=0,d+c+5 do
w((j>d+5 or(i>c-b and j>a+2 and j<d+3)or(i>c-a and j<a))and"#"or(i==c and(j==a+1 and"+"or(j==d+4 and"="or" "))or" "))end
w"\n"end
  • Edit1: Simplified reading
  • Edit2: Removed more whitespaces
  • Edit3: aliases abstraction of io functions inspired by another answer

1

Charcoal, 24 bytes

⊞θ₂ΣXθ²F =+«←←←ι←G↑←↓⊟θ#

Try it online! Link is to verbose version of code. Takes input as an array of two elements. Explanation:

⊞θ₂ΣXθ²

Append the hypotenuse to the inputs.

F =+«

Loop over the characters that appear to the right of each square in reverse order.

←←←ι←

Print that character leftwards with spacing.

G↑←↓⊟θ#

Pop the last number from the array and print a square of #s of that size.


1
@KevinCruijssen Whoa, what an oversight! Should be fixed now.
Neil

1

PowerShell, 139 137 135 bytes

-2 thanks to ASCII-only
-2 thanks to Mazzy

param($a,$b)($c=[math]::sqrt($a*$a+$b*$b))..1|%{(($m=" ","#")[$_-le$a]*$a)," +"[$_-eq1],($m[$_-le$b]*$b)," ="[$_-eq1],("#"*$c)-join" "}

Try it online!

Calculating $c hurt and there's probably a better way to conditionally swap between # and . Builds a list of chunks and joins them together while conditionally adding the signs.


1
there is a redundant brackets in $m=(" ","#"): Try it online!
mazzy

@mazzy Ha ha, whoops
Veskah

0

Japt, 28 bytes

Takes input as an array of integers.

pUx²¬)ËÆDç'#
í"+="¬ûR3)c ·z3

Try it

                    :Implicit input of array U=[a,b]
pUx²¬)ËÆDç'#
p                   :Push
 U ²                :  Square each element in U
  x                 :  Reduce by addition
    ¬               :  Square root
     )              :End push
      Ë             :Map each D
       Æ            :  Map the range [0,D)
        Dç'#        :    Repeat "#" D times
í"+="¬ûR3)c ·z3
í                   :Interleave
 "+="¬              :  Split the string "+=" to an array of characters
      û             :  Centre pad each
       R3           :    With newlines to length 3
         )          :End interleave
          c         :Flatten
            ·       :Join with newlines
             z3     :Rotate clockwise 270 degrees

0

05AB1E, 38 bytes

nOtª©Å10ζíε„ #yè®Rׄ= NĀèð.øý}»R„=+`.;

Takes the input as a list of two numbers (i.e. [3,4]).

Try it online or verify all test cases.

Explanation:

n             # Take the square of each value in the (implicit) input-list
              #  i.e. [3,4] → [9,16]
 O            # Take the same of that list
              #  i.e. [9,16] → 25
  t           # Take the square-root of that sum
              #  i.e. 25 → 5.0
   ª          # Append it to the (implicit) input-list
              #  i.e. [3,4] and 5.0 → [3,4,5.0]
    ©         # Store it in the register (without popping)
Å1            # Change each value to an inner list of that amount of 1s
              #  i.e. [3,4,5.0] → [[1,1,1],[1,1,1,1],[1,1,1,1,1]]
  0ζ          # Zip/transpose; swapping rows/columns, with "0" as filler
              #  i.e. [[1,1,1],[1,1,1,1],[1,1,1,1,1]]
              #   → [[1,1,1],[1,1,1],[1,1,1],["0",1,1],["0","0",1]]
    í         # Reverse each inner list
              #  i.e. [[1,1,1],[1,1,1],[1,1,1],["0",1,1],["0","0",1]]
              #   → [[1,1,1],[1,1,1],[1,1,1],[1,1,"0"],[1,"0","0"]]
ε         }   # Map the inner lists to:
  #          #  Push string " #"
    yè        #  Index each inner list value into this string
              #   i.e. " #" and [1,1,"0"] → ["#","#"," "]
      ®R      #  Push the list from the register
        ×     #  Repeat the character that many times
              #   i.e. ["#","#"," "] and [5.0,4,3] → ["#####","####","   "]
 „=           #  Push string "= "
   NĀ         #  Push the map-index trutified (0 remains 0; everything else becomes 1)
              #   i.e. 0 → 0
              #   i.e. 3 → 1
     è        #  Use it to index into the string
              #   i.e. "= " and 0 → "="
              #   i.e. "= " and 1 → " "
      ð.ø     #  Surround it with spaces
              #   i.e. "=" → " = "
              #   i.e. " " → "   "
         ý    #  Join the map-list together with this string as delimiter
              #   i.e. ["#####","####","   "] and "   " → "#####   ####      "
»             # After the map, join everything by newlines
              #  i.e. ["##### = #### = ###","#####   ####   ###","#####   ####   ###","#####   ####      ","#####             "]
              #   → "##### = #### = ###\n#####   ####   ###\n#####   ####   ###\n#####   ####      \n#####             "
 R            # Reverse the string
              #  i.e. "##### = #### = ###\n#####   ####   ###\n#####   ####   ###\n#####   ####      \n#####             "
              #   → "             #####\n      ####   #####\n###   ####   #####\n###   ####   #####\n### = #### = #####"
  „=+`.;      # And replace the first "=" with "+"
              #  i.e. "             #####\n      ####   #####\n###   ####   #####\n###   ####   #####\n### = #### = #####"
              #   → "             #####\n      ####   #####\n###   ####   #####\n###   ####   #####\n### + #### = #####"
              # (and output the result implicitly)

DnOt©)˜ε'#×y.Dðy×®y-.D)R}ø» was my attempt until I noticed the + and =.
Magic Octopus Urn

@MagicOctopusUrn Yeah, those three spaces and + and = are indeed responsible for the most part of the code. Btw, you can golf 2 bytes in your approach by replacing DnOt©)˜ with nOt©ª, as I did in my current answer. :) I like your use of .D, though.
Kevin Cruijssen

0

Perl 6, 99 bytes

{$!=sqrt $^a²+$^b²;flip map({map {[' ','#'][$^d>$_]x$d,' =+ '.comb[!$_*++$ ]},$!,$b,$a},^$!)X"
"}

Try it online!

Anonymous code block that takes two numbers and returns the full string with a leading newline and three leading spaces and one trailing on each line.

If we can use other characters instead of #, then I can save a byte by replacing '#' with \*.


0

C# (.NET Core), 221, 194 bytes

This feels way too long. This version just loops to construct the string.

EDIT: Ascii-Only with a nice -27 byte golf using the string constructor for serial char additions! Also, ty for pointing out I was using Math.Sqrt not System.Math.Sqrt. This has been adjusted!

(a,b)=>{int c=(int)System.Math.Sqrt(a*a+b*b),j=c;var s="";while(j>0)s+=new string(j>a?' ':'#',a)+(j>1?"   ":" + ")+new string(j>b?' ':'#',b)+(j-->1?"   ":" = ")+new string('#',c)+"\n";return s;}

Try it online!


1
remember the ending semicolon isn't needed, and also System.Math not Math if you're not using interactive
ASCII-only



One thing, I'd remove all using directives to make sure I didn't make a mistake
ASCII-only

1
Oh and since you no longer have the ternary version I don't think you should mention it anymore
ASCII-only
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.