VOCÊS ESTÃO PREPARADOS PARA ESSA THREAD? Vou passar ponto por ponto de todas as coisas que estão escritas aqui e vou explicar uma por uma pra NÃO FICAR NENHUMA DÚVIDA de que o JS não faz isso porque é uma falha da linguagem.
Isso eu expliquei durante a minha live no @cafedebug () o que acontece é que o NaN é um número porque, assim como o Pi, ou o número de Euler, ele é somente um símbolo que representa um valor que não pode ser representado como um número +
Da mesma forma como fazemos na matemática, quando não podemos representar um número, damos a esse número um símbolo, números complexos são o melhor exemplo disso, e nem por isso deixam de ser números.
Além disso essa é outra que sempre colocam, e isso está descrito na especificação do ECMA262 na seção 7.2.14 - item 7. Isso não é estranho, é seguir a regra. 262.ecma-international.org/12.0/#sec-abst…
Além disso a IEEE-754 (a mesma dos float points) ajuda a explicar isso de uma forma bem clara. stackoverflow.com/questions/1565…
Again, números, toda operação matemática no JS ou fora dele está sujeita a arredondamento (262.ecma-international.org/12.0/#sec-nume…), se você não quer que isso aconteça, use o BigInt developer.mozilla.org/en-US/docs/Web…
Esse eu vou abordar como um grupo inicialmente, porque a saída é óbvia essas duas somas parecem ser iguais pra você? Se você quiser entender mais porque isso não é um problema só do #JavaScript MAS DE TODAS AS LINGUAGENS temos um site só pra isso 0.30000000000000004.com
Agora sobre esse aqui especificamente, como você pode ver no tweet anterior, o resultado não é 0.3, então a saída está correta. O problema aqui é muito maior do que todos nós e eu falo disso nesse ponto do vídeo ++
A questão aqui é que a gente só consegue representar números com uma acurácia perfeita em um sistema de base N se o número for um múltiplo dos fatores primos de N, ou seja, no caso da base 10 (comum), os fatores primos são 2 e 5, então todo o valor que possa ser escrito ++
Como uma fração de 2 ou 5, como 1/2 ou 1/5, ou até seus multiplos, como 0.1 que é 1/10, ou 2/10 não vão possuir restos e serão divisões perfeitas, no entanto, números que não são multiplos desses fatores vão ser dízimas, como dividir 10/3 já que 3 não é um fator, temos 3.333... +
Quando estamos tratando com binário, os únicos fatores são muito mais restritos, portanto, os valores 0.1 e 0.2 são representados como uma soma de frações que apresentam o valor mais próximo do resultado final (algo como essa imagem, matemáticos, por favor me corrijam) ++
Como a soma não é exata, o restante somado de 0.1 com 0.2 passa de 0.3, portanto o valor é maior.
Essa é mais complicada, porque envolve uma série de operações matemáticas. Mas a ideia é que, se formos olhar isso pela lente de uma álgebra mais abstrata, temos que GARANTIR que o resultado de uma chamada pra uma dessas funções é o esperado. E a gente faz isso com identidades +
A identidade que permite a gente ter sempre o maior número de uma lista é ter uma lista cujo único elemento é -Inf para o máximo e Inf para o mínimo, afinal qualquer número é maior que -Inf e menor que +Inf. Uma explicação mais completa aqui charlieharvey.org.uk/page/why_math_…
Como eu expliquei nessa outra thread. Somar dois arrays convertem ambos para strings, a representação de string em um array vazio é "" ou seja, concatenar duas strings vazias é ""
Mesmo caso do anterior, você já tentou dar um console.log em um objeto concatenado com uma string? O resultado é o mesmo, a diferença é que estamos somando "" com "[object Object]" que é a representação do {}
Aqui a questão é criação de escopo dinâmico. Sem parenteses, essa expressão traduz como um bloco de código vazio e uma conversão de um array para um número, basicamente como na segunda imagem (o @erickwendel_ já mostrou isso em alguns vídeos), +[] converte [] para número ++
Isso é algo que eu tenho que dar o braço a torcer, porque a representação numérica de um array vazio é sempre 0, mas a representação booleana é sempre true e isso pode confundir, mas se usarmos parenteses, temos o mesmo resultado
True converge para 1 quando convertido para número, se somarmos 3 trues é a mesma coisa que Number(true)*3 que é 3, da mesma forma de Number(true)-Number(true) é 1-1 que é 0
Eu me sinto até meio mal de explicar essa mas então, o operador de comparação abstrada (==) coerce o tipo para manter o mesmo dos dois lados, portanto true == 1 é 1==1 que é true, já a comparação estrita (===) compara TIPO e valor, 1 não é booleano, portanto...
mais uma pegadinha, se pegarmos o valor que está sendo somado dentro da expressão e começarmos a executar ele parte a parte, vamos a expressão que eu vou colocar no próximo tweet ++
O resultado é 'truefalse' que tem 9 caracteres, por isso o resultado é 9. E o porquê disso tudo você pode entender aqui github.com/denysdovhan/wt…
A parada aqui é que o operador de adição pode ser o concatenador de uma string ou uma operação de soma conforme a parte 13.8.1 da Spec do ECMA, já o operador de subtração sempre vai subtrair números, logo ele vai converter o que não é número pra números e executar a operação ++
Por isso 91-"1" é 90, porque o que está acontecendo é 91 - Number(1), já a adição chama realiza uma verificação "EvaluateStringOrNumericBinaryExpression" conforme a specificação ++ 262.ecma-international.org/12.0/#sec-addi…
Essa expressão vai produzir um valor da expressão "ApplyStringOrNumericBinaryOperator" que diz que se qualquer um dos lados for string e o operador for "+" então retorna a concatenação das strings 262.ecma-international.org/12.0/#sec-appl…
Por fim a clássica, como eu falei, eu acho errado o array convergir pra 0 quando é numérico e pra true quando é boolean, mas novamente, todos esses problemas acontecem por conta do "==", o que a gente ta vendo aqui é (+[])==0 que é 0==0, ou seja, true.
Se a gente fizer usando "===" isso vai dar false, mas se a gente converter e comparar com boolean isso também vai dar true
E chegamos ao fim 🎉 o objetivo dessa thread foi justamente pra mostrar pra galera que o JS não é esquisito, ele é perfeitamente normal de acordo com a sua própria especificação e também para incentivar a galera a ler um pouco mais antes de postar sobre isso!
Quem quiser ver as outras threads, essa foi uma:
E logo mais vai ter vídeo lá sobre isso no canal, valeu galera! youtube.lsantos.dev

• • •

Missing some Tweet in this thread? You can try to force a refresh
 

Keep Current with Lucas Santos 🇧🇷🇸🇪

Lucas Santos 🇧🇷🇸🇪 Profile picture

Stay in touch and get notified when new unrolls are available from this author!

Read all threads

This Thread may be Removed Anytime!

PDF

Twitter may remove this content at anytime! Save it as PDF for later use!

Try unrolling a thread yourself!

how to unroll video
  1. Follow @ThreadReaderApp to mention us!

  2. From a Twitter thread mention us with a keyword "unroll"
@threadreaderapp unroll

Practice here first or read more on our help page!

Did Thread Reader help you today?

Support us! We are indie developers!


This site is made by just two indie developers on a laptop doing marketing, support and development! Read more about the story.

Become a Premium Member ($3/month or $30/year) and get exclusive features!

Become Premium

Don't want to be a Premium member but still want to support us?

Make a small donation by buying us coffee ($5) or help with server cost ($10)

Donate via Paypal

Or Donate anonymously using crypto!

Ethereum

0xfe58350B80634f60Fa6Dc149a72b4DFbc17D341E copy

Bitcoin

3ATGMxNzCUFzxpMCHL5sWSt4DVtS8UqXpi copy

Thank you for your support!

Follow Us on Twitter!

:(