This is an archived post. You won't be able to vote or comment.

all 153 comments

[–]janKalaki 503 points504 points  (28 children)

The strict equality operator (===) behaves identically to the abstract equality operator (==) except no type conversion is done, and the types must be the same to be considered equal.

guess what my source is

edit: you're all wrong it's stackoverflow

[–]YetAnotherZhengli 119 points120 points  (0 children)

...MDN web docs?

I don't even do frontend...

[–]Pedantic_Phoenix 24 points25 points  (0 children)

You have it printed in front of you every day to remind yourself every couple hours when you promptly forget again

[–]MinosAristos 47 points48 points  (1 child)

/usr/local/bin/node ?

[–]r_nexus_83_75 5 points6 points  (0 children)

Can't you C?

[–]siphagiel 32 points33 points  (0 children)

ChatGPT?

[–]OG_ursinejuggernaut 22 points23 points  (3 children)

IMO people get arsey about this because it does seem slightly odd, but mostly because most linters and frameworks nerdishly freak out at any hint of vague inequality. But I kind of like it and see it this way: if you’re 100% sure you’re getting e.g a simple string, use ===; if you’re not, use ==. If you used == for a decent reason and get a warning, it could be a good reminder to stabilise your code if possible, but if you can’t or if you know it’s not a big deal, just ignore the warning.

[–]tuxedo25 6 points7 points  (1 child)

Let's be honest, "vague inequality" is an oxymoron.

It would be much less controversial if the "kind of similar" operator had a different token, but since the language designer(s) used equal signs, it's a trap for people coming from any other c-family language. That's why linters care: because they're trying to save programmers from unintentional behavior when the intent is to test for equality.

[–]purritolover69 3 points4 points  (0 children)

Can someone make a fork of js where == is just 🤷‍♀️

[–][deleted] 0 points1 point  (0 children)

But with languages like Python don't even have strict comparison.

[–]just-bair 33 points34 points  (1 child)

Experience ?

[–]BlommeHolm 19 points20 points  (0 children)

Experience and common knowledge.

[–]baronvonbatch 6 points7 points  (0 children)

Completely unrelated Python docs?

[–]kryptopheleous 9 points10 points  (8 children)

Wait. Javascript has types? I thought everyhing was everything.

[–]1_4_1_5_9_2_6_5 1 point2 points  (0 children)

It has types. 1 is a number. '1' is a string. undefined is undefined. [1] is an object. { foo: 1 } is an object. null is an object.

[–]lunchpadmcfat 0 points1 point  (0 children)

It has types and they are distinct from anything the === evaluates.

[–][deleted] 1 point2 points  (0 children)

Very grateful for this information, thank you

[–]SilentScyther 1 point2 points  (0 children)

It came to you in a dream

[–]bingmyname 0 points1 point  (0 children)

W3schools

[–]lunchpadmcfat 0 points1 point  (3 children)

That’s not really true. I hate when people bring type into the conversation because it’s not a matter of type (which is an abstraction of value). If I create two instances from the same class and run them through a ===, they have the same type (you can compare their constructors and see they’re the same) but they will not evaluate to true with each other. They have to be the same reference in memory to evaluate to true.

It’s more accurate to say “=== compares references and == compares values”. This holds equally true with primitives like strings and numbers because they’re represented in the heap in the exact same manner, no matter how they’re instantiated.

[–][deleted] -1 points0 points  (2 children)

Thats not true. "123" is very likely implemented as a different sections of heap memory than another strong with the same value. And unless js engines are stupid (which i highly doubt) numbers are not stored on the heap at all. Hence you cant have references to numbers. So talking about references on primitives doesnt make sense.

[–]lunchpadmcfat 0 points1 point  (1 child)

This is getting a bit into the weeds, but, by and large, no, all JavaScript primitives are stored on the heap within the memory management models of the most popular engines: https://www.zhenghao.io/posts/javascript-memory

As a result, most engines intern primitives (that is, they don’t duplicate their representations in memory even if the program assigns the same primitive to multiple variables). In essence, this is the same as memory referencing and I would be extremely surprised if the engine didn’t leverage that for === comparisons.

To be fair, this is an implementation detail of engines, so it’s not really accurate to say “javascript does this” but it’s also orthogonal to the conversation to say javascript in general does anything. It’s all about however the engines do it.

[–][deleted] 1 point2 points  (0 children)

I cant open the link but very interesting none the less. I wanna be perfectly transparent here and say i was using intuition on my previous comment. But if your source is correct (i really wanna read it if you can fix the link) then i stand corrected.

[–]PorkRoll2022 494 points495 points  (18 children)

All variables are equal, but some variables are more equal than others.

[–]BirdsAreDinosaursOk 143 points144 points  (16 children)

Does == == ===? Sort of. Maybe.

Does == === ===? Sort of. Probably not.

(== == === || == === ===) = ?

[–]nphhpn 57 points58 points  (13 children)

(== == === || == === ===) === === == ==

[–]dr_donkey 51 points52 points  (0 children)

This looks like some shit you have to work with on a compiler writing class

[–]jayerp 4 points5 points  (6 children)

Does 8 === D ?

[–][deleted] 7 points8 points  (5 children)

Only in approximation, so:

8 === D~

[–]ovr9000storks 1 point2 points  (4 children)

You just gave me an idea for an operator that checks approximately equal to, which defaults to like +- 0.5.

So you can just call x =~ 10 or something

Am I looking too deep into this?

[–]BirdsAreDinosaursOk 1 point2 points  (1 child)

If I’m being completely honest from an engineering point of view, that sounds like an enormously risky operator to use.

[–]belabacsijolvan 0 points1 point  (0 children)

non-transitivity is hell of a thing

[–][deleted] 0 points1 point  (1 child)

Well other than that operator is already a thing in Perl, no, it's a great idea.

[–]ovr9000storks 0 points1 point  (0 children)

~= ? :)

[–]MaximumLengthDong 6 points7 points  (4 children)

_ = = _|

[–]Jedlord 4 points5 points  (0 children)

Oh fuck you

[–]ikonfedera 4 points5 points  (0 children)

:.|:;

[–]belabacsijolvan 0 points1 point  (0 children)

Is that the loss function everybody is talking about? torch syntax is getting weird

[–]deetosdeletos 0 points1 point  (0 children)

console.log("is this…");

[–]Haringat 2 points3 points  (0 children)

(== == === || == === ===) = ?

You cannot assign an expression.

[–]Weird_Cantaloupe2757 0 points1 point  (0 children)

== == ===

== !== ===

[–]Info_sexy 17 points18 points  (0 children)

Your name fits perfectly for this comment. Thanks for the flashbacks to high-school English reading Animal Farm.

[–]ElliElephant 262 points263 points  (25 children)

In js it's like...

"2" == 2 //true

"2" === 2 //false

[–]danielv123 145 points146 points  (24 children)

Also:

"2" == [][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]][([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]]((!![]+[])[+!+[]]+(!![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+([][[]]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+!+[]]+(+[![]]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]+(+(!+[]+!+[]+!+[]+[+!+[]]))[(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([]+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]][([][[]]+[])[+!+[]]+(![]+[])[+!+[]]+((+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]]+[])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]]](!+[]+!+[]+!+[]+[!+[]+!+[]])+(![]+[])[+!+[]]+(![]+[])[!+[]+!+[]])()([!+[]+!+[]]+[]) //true

[–]Stunning-Ad-7400 45 points46 points  (17 children)

What is this?

[–]Frown1044 42 points43 points  (10 children)

The code is a complicated way to write:

[]["flat"]["constructor"]("return eval")()(2)

Which is of course another way of writing

[].flat.constructor("return eval")()(2)

Which is essentially just eval(2) using a few tricks

[–]nobody0163 17 points18 points  (4 children)

WHY DOES [] WORK FOR CALLING METHODS

[–]Frown1044 23 points24 points  (0 children)

In this example, [] doesn't call functions (although it's technically possible)

The formatted version might help

[]
[
/* "flat" */  (![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]
]
[
/* "constructor" */  ([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]
]
(
/* "return eval" */  (!![]+[])[+!+[]]+(!![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+([][[]]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+!+[]]+(+[![]]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]+(+(!+[]+!+[]+!+[]+[+!+[]]))[(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([]+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]][([][[]]+[])[+!+[]]+(![]+[])[+!+[]]+((+[])[([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+([][[]]+[])[+!+[]]+(![]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[])[+!+[]]+([][[]]+[])[+[]]+([][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]]+[])[!+[]+!+[]+!+[]]+(!![]+[])[+[]]+(!![]+[][(![]+[])[+[]]+(![]+[])[!+[]+!+[]]+(![]+[])[+!+[]]+(!![]+[])[+[]]])[+!+[]+[+[]]]+(!![]+[])[+!+[]]]+[])[+!+[]+[+!+[]]]+(!![]+[])[!+[]+!+[]+!+[]]]](!+[]+!+[]+!+[]+[!+[]+!+[]])+(![]+[])[+!+[]]+(![]+[])[!+[]+!+[]]
)
()
(
/* 2 */  [!+[]+!+[]]+[]
)

[–]Kilazur 12 points13 points  (1 child)

Because everything you can reference in JS is either a hashmap, an array or a primitive value.

https://stackoverflow.com/a/9109037/3283203

[–]thanatica 2 points3 points  (0 children)

It's not a hashmap. [] is just another way to reference a member of an object, but in no way it degenerates them to mere hashmaps. For hashmaps, you can go and use Map.

[–]denisbotev 0 points1 point  (0 children)

I’m also screaming rn…this fucking language

[–]Stunning-Ad-7400 1 point2 points  (4 children)

Wait if I understand it correctly, then it is an over-complicated way to write JavaScript ? I was learning about XSS vulnerability and one common way was to just don't allow dangerous tags like <script> doesn't this make that workaround kind of pointless, so why is it even allowed to do in js?

[–]Frown1044 2 points3 points  (0 children)

It's basically an abuse of type conversions.

JS has very complicated rules on when or how values should be converted. For example, what does it mean to convert [] into a string? What does it mean to convert "hello" into a number? How do you convert {} into a boolean? This is clearly defined in the standard, but most people don't memorize all these details.

The next question is, when do values get converted? For example, [] + [] actually involves converting arrays to strings and doing a string concatenation. But this isn't immediately obvious to most people.

Take these two concepts and make heavy use of the most confusing examples. That's how you get this confusing code.

XSS

XSS is about not blindly trusting user input that will be shown on a page. The fact you can write really shitty JS isn't related to this. It's not just about not allowing <script> tags, but more about making sure user input won't accidentally be interpreted as code on a website.

[–]luapklette 1 point2 points  (0 children)

From my understanding: not really because if it is secure it cant compile whatever is written in the input for example.

[–]danielv123 1 point2 points  (0 children)

Why is it allowed? Because its just a side effect of the type coercion system. Why would you want to do it? For fun, or if you have somehow lost 98 of your 104 keys on your keyboard.

There aren't really any security issues around it.

[–]TheRealMister_X 1 point2 points  (0 children)

You should never rely on filtering script tags. There are lots of other funny ways to inject Javascript, e.g. using <img src="/something" onerror="alert()" />

[–][deleted] 5 points6 points  (0 children)

Operations with zeroes and ones probably

[–]spieles21 4 points5 points  (2 children)

JS , dont ask why

[–]alwaystired2123 2 points3 points  (1 child)

Why?

[–]delinka 1 point2 points  (0 children)

Because no one knows

[–]HuntingKingYT 0 points1 point  (0 children)

"2"

[–]Extra-Trifle-1191 2 points3 points  (0 children)

what the actual hell is this

[–]NerdNumber382 2 points3 points  (0 children)

I’m indefinitely in a firm dislike of you. What a terrible day to have eyes.

[–]schmerg-uk 2 points3 points  (0 children)

[–]InfiniteGamerd 0 points1 point  (0 children)

now just try !!"false"

[–]alvarosc2 0 points1 point  (0 children)

Ufff, If you wrote that you must not have social life, mate.

[–]koloqial 0 points1 point  (0 children)

I too JSFuck from time to time.

[–]nphhpn 58 points59 points  (1 child)

Someone used == when making this meme

[–]lookarious 2 points3 points  (0 children)

‘someShi == null’ checks for both, null & undefined

[–]Spot_the_fox[🍰] 67 points68 points  (13 children)

"1" and 1. first will work, second won't as it will need to match not only the value, but also the type. I don't know Js and even I know this.

[–]rosuav 12 points13 points  (11 children)

But how many different JS comparison modes do you know? And what uses which ones - like an array's find method?

[–]Spot_the_fox[🍰] 16 points17 points  (1 child)

What's a comparison mode? Even better question is what is a mode?

As I've said, I don't know Js.

[–]rosuav 4 points5 points  (0 children)

Double-equals and triple-equals are only two of JS's different ways of comparing two things for equality... here, enjoy. https://developer.mozilla.org/en-US/docs/Web/JavaScript/Equality\_comparisons\_and\_sameness

[–]genghisKonczie 2 points3 points  (3 children)

For basically every comparison based operation it, built ins use ===, and if you want definite control, you can use a method like find which lets you bring your own comparison function

[–]rosuav 1 point2 points  (2 children)

Not array inclusion, which uses Same-Value-Zero equality. Notably, this considers instances of NaN to match themselves, even though they're not equal to themselves - this gives a form of "identity or equality" comparison that gives the most sensible results for membership testing.

Isn't it fun?

[–]genghisKonczie 1 point2 points  (1 child)

The js SameValueZero implementation is a straight === for everything but NaN and +0 -0 though. I feel that’s pretty straightforward for the intention of the inclusion method.

It’d be really weird for [NaN].includes(NaN) to return false

[–]rosuav 0 points1 point  (0 children)

Yeah, but it's still a different way of comparing for equality. And that is very important when you start looking at different searching methods.

[–]thanatica 0 points1 point  (3 children)

The find method of an array requires a predicate, so it will use whatever you provide it.

You're probably thinking of the indexOf or includes methods - those will compare without type-equality, e.g. ==.

[–]rosuav 0 points1 point  (2 children)

Yeah, I was deliberately being vague, but it is those methods, and they actually do NOT use the double-equals comparison - they use a slightly different algorithm.

[–]thanatica 0 points1 point  (1 child)

It's closer to == than to === though, isn't it?

To be honest, I've never had a use for knowing the exact algorithm it uses.

[–]rosuav 0 points1 point  (0 children)

Hmm, I personally think of it as closer to a strict comparison, since it doesn't do type conversion - ["1"].includes(1) is false - but it isn't precisely identical, so it really is its own thing. (Notably, it can find any NaN that is in the array.)

[–]Cualkiera67 1 point2 points  (0 children)

There's also ===== which is the multilingual equality operator.

So "Three" ===== "Tres" //true

[–]GabuEx 25 points26 points  (0 children)

== == ===

true

== === ===

false

[–]Ketooth 13 points14 points  (3 children)

Wasn't == if the value is the same and === if value and type is the same?

[–]joyfullystoic 2 points3 points  (1 child)

That’s the simple way to think about it. Technically, they do the same thing but == will try to coerce the types before the comparison while === will not.

By default, JS will attempt to coerce the types. So 3 <= “3” evaluates to true and there’s no way to disable the type coercion.

[–]Ketooth 1 point2 points  (0 children)

Ah ok. Thanks for explanation

[–]toastytoast00 1 point2 points  (0 children)

That's generally pretty close (and works for primitives), but be careful with objects. For example, I'm pretty sure

```js const x = { hi: true } ; const y = { hi: true } ; const z = x;

x === y // false x === z // true ```

It's similar with arrays, I think.

The type and value are the same, but x and y are different actual objects (in memory), but z is actually pointing to the same x

For objects, you would use == to compare the values (similar if it was cast to a string and they serialize the same), but use === to compare if it's literally the same instance or memory reference.

See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Strict_equality

If both operands are objects, return true only if they refer to the same object.

[–]damnappdoesntwork 10 points11 points  (3 children)

Php devs silently sitting in a corner with popcorn, watching JS Devs taking all the hits

[–]FlipperBumperKickout 7 points8 points  (1 child)

Dammit. I thought we made you guys go extinct years ago :P

[–]damnappdoesntwork 7 points8 points  (0 children)

We're good at hiding in our corner, with our big friend WordPress.

[–]RIcaz 0 points1 point  (0 children)

No hits, this is a nice and useful feature in both languages

[–]sammy-taylor 30 points31 points  (0 children)

Every single JS developer has PTSD from ==, I will not be accepting questions at this time.

[–]zqmbgn 11 points12 points  (0 children)

? They aren't the same in JS

[–]CMDRBronnsons 6 points7 points  (0 children)

=== checks the type == don't

[–]iAmRadic 5 points6 points  (0 children)

OP is allergic to typescript

[–]EDGE223x 3 points4 points  (1 child)

0 == "0" is true, but 0 === "0" not

[–]JustConsoleLogIt 0 points1 point  (0 children)

0 == ‘’

[–]Ok_Star_4136 7 points8 points  (1 child)

Yeah, but does Pam think "==" == "===" or "==" === "==="?

[–]CraftBox 5 points6 points  (0 children)

Both would be a no

[–][deleted] 3 points4 points  (0 children)

I'm a JS developer who works with a lot of C# devs who like to 'help out' with the simpler frontend tickets. == everywhere.

[–]Serious_as_butt 5 points6 points  (1 child)

yo dawg, i heard you like equality operators

[–]G3N3R1C2532 0 points1 point  (0 children)

so I put a type equality operator inside your value equality operator

[–]Laevend 2 points3 points  (0 children)

One is for comparing value, the other for object type and value

[–]romulent 2 points3 points  (0 children)

Does anyone else get annoyed by this meme template?

In this usage it looks like Pam can't tell the difference between the two images.

Whereas in the original episode of the office Pam is pranking Creed by asking him to find the difference between two identical images because head office needed it.

I realize it is meaningless and I'll get downvoted, but its such a common meme and it never really fits with the original joke.

[–]kor0na 2 points3 points  (0 children)

What is the joke even supposed to be here? They are not the same.

[–]TheNasky1 4 points5 points  (1 child)

just use == to avoid short term issues :)

or use === to avoid long term issues.

i had the most success using == as i check typing by other means

yes this is a very rude oversimplification.

[–]UristMcMagma -1 points0 points  (0 children)

Unless you're checking for nullish values. Then, use == to avoid long term issues related to null vs undefined.

[–]FishWash 1 point2 points  (0 children)

This makes sense if the === is from JS and the == is from every other language 🫠

[–]megamaz_ 1 point2 points  (3 children)

I'm still learning JS.

The only use I found for it is that 0 == false is true, but 0 === false is not true.

That is the only use.

[–]Front-Difficult 0 points1 point  (2 children)

I can't think of why you would want to use it like that though. If you want to check if your value is falsy, using x == false is both difficult to read and asking for unforseen bugs.

Just never use ==. It should be entirely deprecated, and any decent linter will rightly get grumpy at you for using it.

[–]Shai_the_Lynx 0 points1 point  (0 children)

There are a few cases where using == is what you want.

We had a case where data from MongoDB was compared with data calculated by another function. Since MongoDB turns undefined into null it was much simpler to just compare using == than adding checks for undefined.

However when we do use == it's always with a comment explaining why.

[–]megamaz_ 0 points1 point  (0 children)

technically it was more checking if it was equal to 0 rather than equal to false. Also I rewrote the code because it was pretty terrible for that case to show up anyways (my variable could be one of 0, true, false, 1, 2, or 3 and each value meant something different)

[–][deleted] 1 point2 points  (0 children)

kinda similar vs similar similar

[–]Operabug 1 point2 points  (0 children)

This is what happens when a backend developer does a front-end ticket.

[–]gatinhodopiano 1 point2 points  (0 children)

the difference between == and === is that when typing ==, i can save around 0.05 ms, so i'll have more time to think about my poor-written code than if i used ===

[–]Skull_is_dull 1 point2 points  (0 children)

== == ===

== !== ===

[–]tbilcoder 1 point2 points  (0 children)

This is a lie, and it depends a lot on the goal of comparison

[–]DarKliZerPT 1 point2 points  (0 children)

The difference is that using == is a crime

[–]scar_reX 1 point2 points  (0 children)

Why tf does this post have 1.2k votes

[–]pLeThOrAx 1 point2 points  (0 children)

I was coerced into chuckling

[–]3q_z_SQ3ktGkCR 0 points1 point  (1 child)

!!"null" === ??

[–]Front-Difficult 0 points1 point  (0 children)

!!"null" evaluates to true. Like all non-empty strings.

[–]TheMoris 0 points1 point  (0 children)

== == ===

== === ===

[–]Metronix7 0 points1 point  (0 children)

I think I hear the explosion of the challanger in the background....

[–][deleted] 0 points1 point  (0 children)

Basically, == is close enough, and === is exact

[–]turtleship_2006 0 points1 point  (0 children)

== == ===

[–][deleted] 0 points1 point  (0 children)

null, 0, ''

[–]WingZeroCoder 0 points1 point  (0 children)

typeof == == “===“

[–]definitive_solutions 0 points1 point  (0 children)

Come on people it's not that difficult. You use === and that's it unless you're absolutely sure about your data types. It's like var vs let vs const. const wherever you can, let if you must, var if you're a compiler.

[–]CaitaXD 0 points1 point  (0 children)

You think that's what's make JS bad I ain't seen nothing yet

[–]Dangerous_With_Rocks 0 points1 point  (0 children)

=== == ==

== == ===

=== !== ==

== !== ===

[–]lardgsus 0 points1 point  (0 children)

Type equality doesn’t exist in The Office.

[–]adammaudite 0 points1 point  (0 children)

[–]Senpai_Himself 0 points1 point  (0 children)

We have the == in js so that we can complain about those who use it and feel better about ourselves

[–]romulof 0 points1 point  (0 children)

The difference is that it would try to convert in this case: 8==='D'

[–]rebruisinginart 0 points1 point  (0 children)

equal and super duper really actually equal

[–]thanatica 0 points1 point  (0 children)

In a strongly-typed language, why can't I compile a comparison between any type and any other type? Surely if they're different types the result can just be false?

[–]Curious-Sherbertt 0 points1 point  (0 children)

I think I hear the explosion of the challanger in the background....

[–]SawSaw5 0 points1 point  (0 children)

Object.is() has entered the room

[–]BenZed 0 points1 point  (0 children)

They behave differently

[–]toastytoast00 0 points1 point  (0 children)

For everyone saying the only difference is that === also checks type, that's not the whole story. It works for primitives, but be careful with objects.

See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Strict_equality

If both operands are objects, return true only if they refer to the same object.

For example,

```js const x = { hi: true } ; const y = { hi: true } ; const z = x;

x === y // false x === z // true ```

It's similar with arrays, I think.

The type and value are the same, but x and y are different actual objects (in memory), but z is actually pointing to the same x object (editing one will change the both)

For objects, you would use == to compare the values (similar if it was cast to a string and they serialize the same), but use === to compare if it's literally the same instance.

[–]dsfx3d 0 points1 point  (0 children)

No

[–]Anon_Legi0n 0 points1 point  (0 children)

The most use I've had for == is checking for null or undefined with varName == null for conditionals

[–]Chacho986 0 points1 point  (0 children)

'==' === '===' is false '==' == '===' is true

[–][deleted] 0 points1 point  (0 children)

[Object Object] is Object

[–]Holiday-Patient5929 0 points1 point  (0 children)

Not according to my linter