03:32 | <jschoi> | FYI: A late-breaking pull request has been opened for Observables with slides. https://github.com/tc39/agendas/pull/1846, https://docs.google.com/presentation/d/1i5_zneksrU7i7ZHcl5EQRzUHGkmXRIQKd-bLfrPRNXY/edit?usp=sharing |
13:51 | <ryzokuken> | @room starting in 10 minutes! |
14:12 | <Jesse> | please add yourself to the attendees list in the doc if you're here! |
14:12 | <Jesse> | (I'm not exactly a newbie when taking notes, but I don't know everyone's abbreviation 100%, I usually go to the attendee list when I'm unsure) |
14:12 | <dminor> | Question about the next meeting, are we confident enough that A Coruña will be in person that delegates can start making travel plans? |
14:13 | <Michael Ficarra> | it's easier to just keep https://github.com/tc39/notes/blob/main/delegates.txt open |
14:14 | <Michael Ficarra> | I've already booked my travel 😬 |
14:14 | <ryzokuken> | yes |
14:15 | <ryzokuken> | sorry I have no idea why it seemed unclear on the chairs' end: this is most certainly a confirmed meeting, please feel free to book travel |
14:15 | <ryzokuken> | the interest survey was sent out earlier than usual |
14:16 | <Michael Ficarra> | it seems weird to have a domain-agnostic "structured data" TC |
14:16 | <littledan> | tell that to TC49, "programming languages" |
14:16 | <Michael Ficarra> | I imagine it would require participation from experts in each of the respective (and disparate) domains |
14:17 | <littledan> | it would, yes. We won't fully found it if we don't get those experts, but initial discussion with the open source communities tends positive |
14:17 | <Michael Ficarra> | yeah, that's weird and obviously too broad |
14:17 | <littledan> | well... it's just normal. We also feed into ISO/IEC JTC1 SC22, which is also programming languages... |
14:17 | <littledan> | note that this TC proposal hasn't been announced publicly |
14:18 | <littledan> | (at Ecma's request) |
14:18 | <Michael Ficarra> | I guess you'll have separate TGs that basically don't overlap at all? |
14:21 | <shu> | what is the upshot of ecma involvement in C#, if that's an analogy here? |
14:22 | <jschoi> | I’ve been excited about this initiative ever since I heard about it last plenary. |
14:22 | <littledan> | the development of C# takes place in https://github.com/dotnet/csharplang yet we standardize it in TC49 later |
14:22 | <littledan> | TC39's model of doing development in committee is just one possible model, which some TCs follow and others don't |
14:23 | <shu> | what does one get out of the standardization in TC49 |
14:23 | <Michael Ficarra> | maybe obscure government requirements? |
14:24 | <littledan> | I don't know much about C#, but for CycloneDX and JSON Schema, there's also need to normatively reference things from other specs, and we've also seen in CycloneDX that creating a standards committee can attract engineering effort to do detailed reviews which just weren't happening on the open source side alone |
14:24 | <littledan> | I'm very hopeful that we'll get this last sort of value out of the JSON Schema effort, and also that it will help people rally around this version |
14:25 | <littledan> | yeah but there's also proposed to be a "methodology" TC to find common requirements for such languages and schemas (schemata?) |
14:33 | <jschoi> |
|
14:33 | <jschoi> | It always amuses me how fifteen minutes are allowed to Chip’s “update”. |
14:35 | <Chris de Almeida> | oh, the agenda numbers for the boilerplate stuff should probably get updated. on the schedule and TCQ it is 1m |
14:35 | <Aki> | when i was handling scheduling I used it as agenda timeslot breathing room |
14:36 | <Steve Hicks> | Chris de Almeida: Not sure what the procedure is or if I'm too late, but I can loosen my constraint to include availability the first hour of Day 4, which if we can swap the two topics that morning would unblock all constraints for Disposable AsyncContext. |
14:37 | <jschoi> | 🫁 |
14:42 | <Chris de Almeida> | ok, we'll see what we can do. please submit a PR to the agendas repo to update your constraint 🙂 |
14:58 | <Michael Ficarra> | I agree with @shu: Nicolò is really good at giving clear presentations |
15:06 | <shu> | i still don't understand mark's concern |
15:07 | <shu> | it's the promises themselves escaping? |
15:07 | <shu> | it doesn't seem like a performance thing he's worried about |
15:07 | <Michael Ficarra> | if a value escapes 262 via a host hook, I consider it accessible to user code |
15:08 | <shu> | what is the problem in this case if this promise becomes accessible to user code? |
15:08 | <Michael Ficarra> | no idea |
15:10 | <littledan> | I'm not sure what Mark meant by "Mathieu will be present at the plenary"--this is the plenary |
15:10 | <littledan> | more note-takers would be nice! |
15:13 | <Michael Ficarra> | I understood it as "at some other point during plenary, but not now" |
15:13 | <Chris de Almeida> | yeah I think he expected him to be here, but is not currently for whatever reason |
15:15 | <shu> | did he say V8 already does this? sweet |
15:19 | <Aki> | could the transcriber not be adding all the newlines? |
15:19 | <Aki> | or is that a technical constraint for some transcribers but not others? |
15:19 | <littledan> | we could interrupt the meeting to ask them |
15:20 | <littledan> | yeah some transcribers have more broken setups than others |
15:20 | <ryzokuken> | should I? |
15:20 | <littledan> | and asking them to change it usually leads to confusion on their part |
15:20 | <littledan> | maybe we should do it anyway? |
15:20 | <littledan> | we also have some quality variability; this transcriber seems not as good as others |
15:20 | <littledan> | but we can't tell the person "be better"; we can just tell the company "transcription was good at this time and bad at that time" |
15:21 | <littledan> | sure, and also say that they can ask for people to go more slowly or for clarification |
15:21 | <ryzokuken> | okay |
15:21 | <ryzokuken> | I'll interrupt the presentation after this slide |
15:22 | <ryzokuken> | let us know if issues persist |
15:22 | <littledan> | let's write an email to the company. Ujjwal, do you have their contact? |
15:23 | <ryzokuken> | during the break we could email them |
15:23 | <ryzokuken> | yeah |
15:23 | <Jesse> | no notes atm? |
15:23 | <littledan> | let's also tell them about this quality variability |
15:23 | <Jesse> | nvm |
15:23 | <ryzokuken> | are they back Jesse ? |
15:23 | <Jesse> | yes |
15:23 | <ryzokuken> | great |
15:24 | <littledan> | they seem increasingly delayed |
15:24 | <littledan> | this is a technical issue that they have had previously and fixed... |
15:24 | <littledan> | eh maybe not so far behind |
15:25 | <nicolo-ribaudo> | dminor: Could we get to your point at the end of the presentation? (there are still a couple slides not about use cases, specifically about the web integration) |
15:26 | <dminor> | Ok, sorry, I thought everything had been presented |
15:28 | <littledan> | To note takers: you can edit the notes to make everything more clear; they are very inaccurate and have a lot of errors. If you put in complete sentences that get across the point, that's better than nonsensical words that might be closer to what was actually said. |
15:35 | <nicolo-ribaudo> | shu Imagine you have two separate functions: one that takes a callback, and another to actually run the callback taken by the first one. Old mental model: the context is propagated from the one that takes the callback |
15:35 | <shu> | that part i got, but i don't understand how the new mental model works with the setTimeout example Andreu gave |
15:35 | <shu> | how can the new mental model work for setTimeout if the timeout callback isn't the one that captures the AsyncContext? |
15:37 | <nicolo-ribaudo> | setTimeout both takes the callback, and is the API that you call to ask the browser to at some point run that API. It flows across the awaits, rather than together with the callback |
15:38 | <ryzokuken> |
|
15:39 | <littledan> | that's their response? |
15:39 | <ryzokuken> | no they emailed me first |
15:39 | <ryzokuken> | I CC'd you on my response |
15:42 | <Chris de Almeida> | what's ironic is that Ujjwal's email contains excessive linebreaks 😄 |
15:43 | <ryzokuken> | wait really? it's just two lines total 😛 |
15:43 | <ryzokuken> | and my name I guess that's a third line |
15:43 | <Chris de Almeida> | on my client it's 4 lines |
15:44 | <ryzokuken> | oh I guess it's trying to wrap to a certain character limit |
15:52 | <littledan> | For more on the web integration for AsyncContext: https://github.com/tc39/proposal-async-context/blob/master/WEB-INTEGRATION.md |
15:53 | <littledan> | For more testimonials from frontend frameworks: https://github.com/tc39/proposal-async-context/blob/master/FRAMEWORKS.md |
15:58 | <ptomato> | shu: issues that I mentioned: https://github.com/tc39/proposal-intl-era-monthcode/issues/32, https://github.com/tc39/proposal-intl-era-monthcode/issues/30, https://github.com/tc39/proposal-intl-era-monthcode/issues/27, plus various bikeshedding threads about updating the era codes provided by CLDR |
16:17 | <ljharb> | oof, hard wraps bad |
16:18 | <ryzokuken> | not my client! I get wrapping while typing and no wrapping while viewing personally. |
16:21 | <Aki> | Regular reminder to provide Summary and Conclusion in notes. Protip: your summary is generally going to be the summary of what you presented. That means in theory you should be able to write it at the same time you write your slides. |
16:21 | <Chris de Almeida> | the original email sent was not wrapped. your response wrapped both the original email in the chain and your new one... 🤷 |
16:22 | <jschoi> | I can see the point of https://sembr.org/ at least in version control. |
16:23 | <ryzokuken> | I love the idea from ptomato where you put the proposed summary as your last slide |
16:23 | <ptomato> | I didn't do it this time, sorry |
16:23 | <ryzokuken> | saves you time and you get it 80% or more correct anyway |
16:23 | <ryzokuken> | you're too cool for it already /s |
16:24 | <ryzokuken> | but yeah I actually stole the idea from your previous presentations because it made so much sense |
16:30 | <ljharb> | yeah i'd never heard of that before until tab referenced it in a pattern matching call last year. i love hard breaking after the end of a sentence - but i think hard breaking in the middle of a sentence is too arbitrary |
16:30 | <ljharb> | that really only works for updates tho, right, since you can't safely predict the outcome of advancement? |
16:31 | <ryzokuken> | skip the advancement but you can still summarize the contents of your presentation |
16:32 | <littledan> | yes and the summary should also include the main discussion points that people brought up |
16:32 | <littledan> | well I like how ptomato put his hoped-for conclusions on consensus in there too |
16:33 | <ryzokuken> | this but it's a "good ending/bad ending/pacifist ending" type meme video |
16:36 | <jschoi> | When moving to the next agenda item, should it be a point of order when the second-to-most-recent agenda item has no main discussion points written yet? This would force all agenda items except the most-recent item to have discussion points written down. |
16:43 | <Michael Ficarra> | please no |
16:43 | <ljharb> | we've talked about that before, but the general feeling was that that'd be too disruptive and slow down plenary too much |
16:43 | <Michael Ficarra> | sometimes you're too busy participating in the next topic but can get to it at break or after the meeting |
16:44 | <Michael Ficarra> | we just don't need hard rules here |
16:44 | <Chris de Almeida> | <insert joke about stop coercing things> |
16:44 | <ljharb> | the only thing that must be written down imo is the outcome of a decision if one is made (or not made), the rest is just very very nice to have |
16:44 | <Chris de Almeida> | we have, in the past, paused to actually do it, but we had mixed results and some folks very much did not like it |
16:45 | <Aki> | false. accurate minutes have to be produced. |
16:45 | <jschoi> | It could be…a point of order at the next day’s meeting. (This would not work for the last day’s meeting.) |
16:46 | <ljharb> | but they don't have to be verbatim, such that we'd need to pause the meeting to get them down, do they? |
16:46 | <ljharb> | also isn't the transcriptionist mostly covering that? |
16:46 | <Aki> | no |
16:46 | <Aki> | they do not |
16:46 | <Aki> | no |
16:46 | <Aki> | the notes are not the minutes |
16:46 | <Aki> | the minutes are a summary of what was discussed |
16:47 | <ljharb> | ah ok |
16:49 | <jschoi> | https://github.com/tc39/notes/blob/af9ce7e48fbb35190b24a042c9b6172ce5c8a1f5/meetings/2024-12/december-04.md#speakers-summary-of-key-points |
16:49 | <jschoi> | What did the minutes say for this one? |
16:50 | <jschoi> | Were merely the “Conclusions” (which, unlike the Speaker’s Summary, were filled out) used? |
16:55 | <littledan> | no because almost all of the time, none of this is written until after the meeting, but it does get written |
16:55 | <littledan> | the point of order should be more about whether we have consensus and such |
16:56 | <littledan> | people generally don't end up wanting to dictate a good summary during the meeting (when they do dictate it, it doesn't tend to be good enough) |
16:57 | <littledan> | the most helpful thing would be if more people helped with fixing up the notes, both during and after the meeting |
16:57 | <littledan> | the goal is to be coherent and intelligible and make the important points -- it's OK if you change words to make this happen |
17:00 | <jschoi> | “You are an amazing technical copyeditor. The following input text is transcribed notes from a technical standards meeting, formatted in Markdown. Reword the dialogue to be coherent, intelligent, and make the important points. It’s OK if you change words to make this happen. Do not change the acronyms at the beginning of each paragraph. Do not change the headings. <input-text>…” 🥲 |
17:00 | <Aki> | actually not allowed believe it or not |
17:00 | <Aki> | ISO is very clear about this |
17:00 | <ljharb> | shitposting is for tdz :-p |
17:05 | <littledan> | the new notetaker is good again! |
17:33 | <bakkot> | kinda like the idea of having a conventional .composite() method which gives you a composite representation of your object |
17:34 | <bakkot> | when your object is conceptually immutable like Temporal objects then it could cache the result internally |
17:34 | <Michael Ficarra> | does a chair wanna shift my topics down so they're back-to-back? /cc @Chris de Almeida @ryzokuken |
17:34 | <jschoi> | bakkot: Did you mean to put a summary about #2600 / Array.fromAsync into the “Normative: Mark sync module evaluation promise as handled” section? |
17:35 | <bakkot> | oops |
17:35 | <Michael Ficarra> | protocol please! |
17:35 | <bakkot> | fixed |
17:35 | <ryzokuken> | wait where's your next topic |
17:35 | <bakkot> | Michael Ficarra: even if there's a protocol it should have a conventional string name |
17:35 | <Michael Ficarra> | @ryzokuken I mean TCQ |
17:35 | <bakkot> | but yeah a protocol that Composite used could be fun |
17:36 | <ryzokuken> | oops sorry I moved Kevin's |
17:36 | <bakkot> | so you look up the symbol key first and if it's there you use that and if not you do the factory function thing |
17:36 | <ryzokuken> | done |
17:36 | <ryzokuken> | sorry for the confusion |
17:36 | <Michael Ficarra> | thanks |
17:37 | <Michael Ficarra> | TCQ topics should have a "push me lower in the queue" button |
17:39 | <Chris de Almeida> | https://github.com/bterlson/tcq/issues/8 |
17:39 | <Michael Ficarra> | https://github.com/bterlson/tcq/issues/69 |
17:40 | <Michael Ficarra> | not edit/remove, just move down, it's different |
17:40 | <Chris de Almeida> | there's also https://github.com/bterlson/tcq/issues/16 |
17:41 | <Chris de Almeida> | I wonder how that TCQ reloaded project is going 🤔 |
17:41 | <Michael Ficarra> | it's a web app, how hard could it possibly be? |
17:52 | <bakkot> | littledan re "ways to avoid people using these for deep immutable structures", not having syntax will go a long way I think |
17:52 | <littledan> | I agree, but I also don't know what the bad part is about the possible future evolution that Ashley mentioned |
17:53 | <littledan> | (I understand "this makes canonicalization unworkable") |
17:54 | <littledan> | I'm still wondering about the GC thing even if we don't allow them in WeakMaps and WeakRefs. Won't it still be hard to manage the interning table's memory, so you can collect unused things? |
17:56 | <littledan> | I don't think symbol sorting is a fatal flaw of canonicalization -- we can just ban unregistered symbol keys, like R&T did. |
17:57 | <bakkot> | Michael Ficarra: your point about "this should use SameValue because it's observable" is directly contradicted by your immediately preceding "we don't need to sort because it's only Composite.equals not actual equality" |
17:57 | <ljharb> | we don't need to sort because the order in which the keys are compared doesn't matter |
17:58 | <bakkot> | if we don't care about key order for use in set/map/etc, even though it's observable, then we definitely don't have to care about -0 vs 0 in the same context, even though it's observable |
17:58 | <ljharb> | it's not about ordering for me for -0, it's that you can't get a -0 key out of a Map or value out of a Set, but you can get it out of a Composite. |
17:59 | <bakkot> | sorry, was having trouble with my mic |
17:59 | <bakkot> | you can get the ordered keys out too |
17:59 | <jschoi> | eemeli: Your video is on, just in case this was accidental. |
18:00 | <littledan> | we had such a big fight about people insisting that R&T use SameValueZero, not SameValue, and this made canonicalization and implementations more complex, which was a big factor in the proposal not moving forward. I'm kind of astounded that, after that, we're talking about going in the other direction, when nothing has changed with respect to -0 from that previous proposal. |
18:00 | <ljharb> | sure. but you can't ever have a -0 key in a Map, or a -0 value in a set |
18:00 | <bakkot> | ok? |
18:00 | <ljharb> | but you can get a -0 key out of a Composite |
18:00 | <bakkot> | I don't know why that implies anything about whether this should use SameValue or SameValueZero |
18:01 | <littledan> | we could also define normalization in terms of +0 for Composites and drive things on that, but I don't see the point |
18:01 | <bakkot> | we definitely don't want to canonicalize -0 in composites |
18:01 | <littledan> | I mean, we could do it just when used as Map/Set keys |
18:01 | <littledan> | but yeah I agree, that'd be silly |
18:01 | <ljharb> | to be clear there's at least 2 of us that think that Map/Set using SameValueZero was a mistake, and that we shouldn't further that mistake here |
18:02 | <littledan> | we should be establishing such understandings of mistakes by consensus, like we did via @@species. Other people feel the opposite way, I think. |
18:02 | <ljharb> | that would be ideal, sure, but each of us is allowed to hold those kinds of beliefs and use them to inform our positions even sans consensus |
18:03 | <Justin Ridgewell> | Isn't it weird that new Set([0]).has(-0) and new Set([Composite(0)]).has(Composite(-0)) would be different? |
18:03 | <bakkot> | it is a lot weird |
18:04 | <ljharb> | a composite is a brand new thing |
18:04 | <nicolo-ribaudo> | Fyi Mark, let x = {}; new Object(x) === x is true |
18:04 | <bakkot> | the point of a composite is that it composes multiple values for use in Sets etc |
18:05 | <bakkot> | it should not also change how those things are compared in Sets |
18:05 | <ljharb> | (also Promise.resolve(promise) === promise for any promise) |
18:05 | <ljharb> | composing IS changing that |
18:05 | <bakkot> | no it isn't |
18:05 | <Michael Ficarra> | it's not, you've been fooled by the coercion in the example |
18:06 | <bakkot> | from a users point of view the fact that the coercion happens is irrelevant |
18:06 | <littledan> | maybe this should be part of our process discussion |
18:06 | <Michael Ficarra> | it's not because you can look at the Set and see that it does not in fact have -0 |
18:06 | <bakkot> | the way users can and do think of this is that Set/Map compare -0 as equal to 0 |
18:06 | <ljharb> | that's a strange statement from "stop coercing things" :-p |
18:06 | <bakkot> | something which ~ no people do |
18:07 | <ljharb> | if you want to run a topic on it in a future plenary sure, but it's entirely distinct from the consensus topic, if that's what you mean |
18:07 | <Michael Ficarra> | if you want an actual understanding of what's going on, you do, and that's who we're talking about right now |
18:07 | <bakkot> | no, we're talking about the behavior of new Set([Composite(0)]).has(Composite(-0)) |
18:08 | <Michael Ficarra> | that is a statement that appears to me to be obviously false |
18:08 | <Michael Ficarra> | like, look, they're different things |
18:08 | <bakkot> | just you though |
18:08 | <Michael Ficarra> | they're symbolically different! |
18:08 | <bakkot> | who cares? |
18:08 | <bakkot> | 0 === -0 and Composites are for composing equality for Sets |
18:09 | <Michael Ficarra> | something weird has to happen to make them the same |
18:09 | <bakkot> | the weird thing is that 0 === -0 |
18:09 | <bakkot> | but that thing has already happened |
18:09 | <shu> | yeah the weird thing is a well known cross-language, widely known IEEE fact? |
18:09 | <bakkot> | Composite({ x: 0, y: 1 }) and Composite({ y: 1, x: 0 }) are also symbolically different |
18:09 | <bakkot> | but as you very correctly point out, they should still be considered equal for purposes of Set |
18:09 | <bakkot> | because the point of Composites is to compose equality |
18:10 | <bakkot> | not to also do some weird key ordering stuff |
18:10 | <ljharb> | right, but what kind of equality. we have 4 i think |
18:10 | <ljharb> | and the one maps and sets use is the weird one |
18:10 | <bakkot> | SameValueZero |
18:10 | <bakkot> | the kind Sets use |
18:10 | <littledan> | Michael Ficarra: What did you think about all of this when we were discussing R&T previously? |
18:10 | <ljharb> | right but that's the weird one. |
18:10 | <bakkot> | we're talking about Sets |
18:10 | <bakkot> | and other things which already use SameValueZero |
18:10 | <littledan> | also ljharb I thought you wanted this behavior too? |
18:11 | <ljharb> | R&T was syntax at that point, this is different |
18:11 | <littledan> | What does it being syntax change? |
18:11 | <littledan> | you didn't need to use R&T syntax to use the feature |
18:11 | <ljharb> | composites and R&T are different beasts, i'm not sure why those discussions dictate these |
18:11 | <ljharb> | sorry, not syntax, primitives |
18:11 | <littledan> | ah OK thanks for clarifying |
18:11 | <littledan> | so... why does that change what's appropriate? |
18:12 | <littledan> | Not saying the discussions dictate it, just trying to follow the logic |
18:12 | <Michael Ficarra> | these have identity and we're talking about a built-in function, not SameValue or strict equality as applied to them |
18:12 | <ljharb> | R&T were Map and Set analogues. Composite isn't. |
18:12 | <ljharb> | so it's not so clear-cut that they must match what Map and Set do. |
18:13 | <littledan> | what are Map and Set analogues? |
18:13 | <bakkot> | the whole point of Composite is for use in Map and Set |
18:13 | <littledan> | OK, could you trace the next step in the logic here for how it connects to what Map and Set should do? |
18:14 | <bakkot> | (and things like includes which also use SameValueZero) |
18:14 | <Michael Ficarra> | @bakkot there's nothing like includes , it's the only thing in the spec that uses it |
18:14 | <ljharb> | yeah includes is also weird :-/ [0].includes(-0) is obviously wrong, because they're different things |
18:14 | <Michael Ficarra> | again, SameValueZero is weird |
18:15 | <ljharb> | it's also very very easy to get SameValueZero semantics if you want them; it's very very hard to unget them if you don't |
18:15 | <bakkot> | it is obviously right because -0 === 0 |
18:15 | <ljharb> | sure, so [NaN].includes(NaN) must be false then? |
18:15 | <ljharb> | the obviousness isn't about === it's about what the literal values are |
18:15 | <bakkot> | no because if you're asking if something includes NaN, and it does, then the answer is "yes" not "no" |
18:16 | <ljharb> | and [0] doesn't include a negative zero, it only has a positive zero in it |
18:16 | <ljharb> | the question is using "is" semantics, not "===" semantics |
18:16 | <bakkot> | but it does include a zero and -0 is a zero |
18:16 | <bakkot> | anyway, this ship has sailed |
18:16 | <bakkot> | I don't care to convince you that Map and includes have the right semantics |
18:17 | <ljharb> | for the existing things ofc. i'm explaining why they're weird and shouldn't be followed for new things |
18:17 | <bakkot> | only that they do have the semantics that they do, and that the point of Composite is to compose existing things not change how they work |
18:17 | <ljharb> | and -0 and 0 are observably different existing things. |
18:17 | <ljharb> | i don't see Composites as only for Map and Set, maybe that's the difference |
18:17 | <ljharb> | it's not CollectionComposite or something, it's "compose multiple values", which is much broader |
18:18 | <bakkot> | Composite({ x: 0, y: 1 }) and Composite({ y: 1, x: 0 }) are also observably different |
18:18 | <Michael Ficarra> | Map and Set are not precedent for SameValueZero because 1) they don't use it and 2) there is no observable difference between the cases where they would use them |
18:18 | <bakkot> | compose for what purpose? to use as a key in a Map or Set |
18:18 | <kriskowal> | My weak intuition is that if 0 and -1 are not meaningfully different in the relevant domain, 0n is right there. |
18:18 | <bakkot> | if you aren't putting them in a Map or Set you can just use a regular object |
18:18 | <Michael Ficarra> | not via Composite.equals they're not |
18:19 | <ljharb> | not if i want trivial equality checks like Composite.equal |
18:19 | <bakkot> | well, neither are Composite({ x: -0 }) and Composite({ x: 0 }) |
18:20 | <Michael Ficarra> | we have a choice there, and I say those should be different |
18:20 | <bakkot> | your argument is circular |
18:20 | <Michael Ficarra> | we have a completely unconstrained choice, we should not choose to go down the SameValueZero route |
18:20 | <bakkot> | you say they should be different because they're observably different via Composite.equals because you want them to be different |
18:20 | <Michael Ficarra> | yes! I want them to be different! |
18:21 | <bakkot> | ok but you can't make the argument based on Composite.equals |
18:21 | <bakkot> | because you are arguing what the behavior of Composite.equals should be |
18:22 | <bakkot> | my point is that we all agree that Composite({ x: 0, y: 1 }) and Composite({ y: 1, x: 0 }) are observably different, but that this does not imply they should be different for the purposes of Composite.equals |
18:22 | <bakkot> | so "these values are observably different" is not sufficient to argue that things should be different from .equals |
18:22 | <Michael Ficarra> | I am not making the argument base on Composite.equals, I am saying that 1) for composites, we need not take into account their SameValue or strict equality when deciding whether keys need to be observably in the same order for Composite.equals, and 2) all non-Composite values should be compared using SameValue because there's nothing else constraining us and that's the best choice |
18:23 | <bakkot> | the thing constraining us is how Map and Set already work |
18:23 | <Michael Ficarra> | it's not, and I've explained that quite clearly |
18:23 | <ljharb> | the way ashley described the argument to Composite to me is that the object is just a named list of positional arguments - it could also be Composite(0, 1) or Composite([0, 1]) and be conceptually the same |
18:23 | <bakkot> | no |
18:23 | <bakkot> | you have asserted otherwise |
18:23 | <bakkot> | and yes I know they do not mechanically work that way anymore |
18:23 | <ljharb> | meaning that conceptually the top-level order is irrelevant for comparison |
18:23 | <bakkot> | but again, this is completely irrelevant for users |
18:24 | <ljharb> | for some number of them. but we're users too. |
18:24 | <bakkot> | for users, you think of Map and Set as using SameValueZero |
18:24 | <bakkot> | we even added an editorial note about that |
18:24 | <Michael Ficarra> | it's unobservable which comparison operation Maps and Sets use! how can it be precedent? |
18:24 | <ljharb> | and Composite isn't Map or Set. |
18:24 | <bakkot> | because this is the correct mental model for users to have |
18:24 | <ljharb> | then that's probably a core point of disagreement |
18:25 | <shu> | are there key sorting concerns with -0, or just anonymous symbol keys? |
18:25 | <bakkot> | just anonymous symbol keys |
18:26 | <ljharb> | that concern only applies if equality is order-dependent, tho, yes? |
18:26 | <bakkot> | anonymous or same-named |
18:26 | <Michael Ficarra> | @shu I don't think anyone wants keys to be sorted, either for comparison or for enumeration |
18:26 | <bakkot> | well, Shu wanted canonicalization |
18:26 | <shu> | am i anyone |
18:26 | <bakkot> | and you can't canonicalize without ordering |
18:26 | <shu> | i don't think i want ordering per se |
18:26 | <Michael Ficarra> | ah, fair, I thought we had given up on that |
18:26 | <shu> | but i also don't care about global communication channel here |
18:27 | <shu> | so if i strengthen my position on canonicalization we might need to find another way to compromise on that, or be at an impasse |
18:27 | <ljharb> | so wait, did composite not get stage 1? |
18:27 | <shu> | it did |
18:27 | <shu> | these aren't stage 1 concerns afaict? |
18:27 | <ljharb> | oh ok cool, it's not in the notes yet |
18:27 | <ljharb> | correct |
18:29 | <bakkot> | Michael Ficarra ^ |
18:29 | <shu> | man f'ing matrix |
18:29 | <shu> | can't see the image |
18:29 | <ljharb> | yes that's the one place |
18:29 | <bakkot> | see the right hand side |
18:29 | <bakkot> | where we say "as in Map and Set methods" |
18:29 | <ljharb> | Map and Set could be specified to use it, instead they canonicalize to +0 , but they're semantically equivalent |
18:30 | <bakkot> | specifically we did this because it is how users understand it to work |
18:30 | <Michael Ficarra> | yeah like has |
18:30 | <bakkot> | and it is how users should understand it to work |
18:30 | <ljharb> | (fwiw i don't think it's relevant that Map/Set aren't written to use the AO, they still use SameValueZero conceptually) |
18:31 | <ljharb> | did we even debate that? it was in es2016, and it was only deferred from 2015 for mootools - i suspect the choice was made from the same (imo wrong) intuition that led to Map and Set using it |
18:31 | <bakkot> | it's a picture of the description of Number::SameValueZero where we say it is "to test for value equality, ignoring the difference between +0 and -0, as in Array, Map, and Set methods" |
18:32 | <ljharb> | iow i think all 3 of those places were chosen at the same time, pre-ES6, and thus invented a new kind of equality |
18:32 | <waldemar> | That capybara (on the slide) likes to live dangerously |
18:32 | <bakkot> | they invented a new, better kind of equality |
18:32 | <bakkot> | === is almost the thing you want, except for NaN |
18:32 | <littledan> | I think the first thing to resolve is whether the overall model that Ashley put out there is a good one (Shu raised doubts which we need to work through), and then the SameValue vs SameValueZero question is a smaller one within that. |
18:32 | <littledan> | so I'd really like to hear more concerns about that broader question |
18:33 | <Michael Ficarra> | replaceability is the right kind of equality |
18:34 | <littledan> | this would only be met by identity-wise canonicalization as Shu proposed |
18:34 | <shu> | to repeat: my broader stage 1 question is how commital are people, really, about the keys vs immutable data use case? big part of V8's performance feedback was contradictory performance expectations were in play. if you leave the design space flexible enough for a glorious immutable data future, then we're back in the same place |
18:35 | <bakkot> | I personally would like to commit to the "composite key" case |
18:35 | <bakkot> | makes a lot of things simpler |
18:35 | <bakkot> | no prototypes, for example |
18:36 | <shu> | and my view is composite keys is cool w/ me. highly skeptical of immutable data |
18:36 | <littledan> | Queue: 1 Reply: this contradicts your previous topic Kevin Gibbons 2 New Topic: Why not "new Composite()"? Eemeli Aro (@mozilla) 3 New Topic: Should either lean in or out more; e.g. "Key" or "Record" rather than "Composite". Eemeli Aro (@mozilla) 4 New Topic: +1 for stage 1 <EOM, won't be present when this is read> Jordan Harband (@herodevs @tc39 ) 5 New Topic: support stage 1 </end> Chris de Almeida (@IBM) 6 New Topic: SpiderMonkey team supports Stage 1 <eom> Daniel Minor (Mozilla Corporation) |
18:37 | <jschoi> | Invited experts can’t block; can they give support? |
18:38 | <shu> | to be frank, my read of ashley's answer of "in the future i'd like my keys and data to be one and the same" is champions aren't completely committed |
18:38 | <shu> | IME you do not design hash table keys to be the same as your data |
18:38 | <shu> | you need to do work to figure out what are the things you key on |
18:38 | <bakkot> | not writing a lot of Java huh? |
18:38 | <shu> | wow do they really do that? |
18:38 | <littledan> | yes definitely |
18:39 | <bakkot> | well, Java you define hash and equals and that is the normal way of things |
18:39 | <bakkot> | and you do that for your normal values |
18:39 | <Michael Ficarra> | on everything, it's ludicrous |
18:39 | <bakkot> | and then stick them in maps |
18:39 | <shu> | and you... just key on arbitrarily complex graph-of-objects? |
18:39 | <bakkot> | uh huh |
18:40 | <shu> | wtf |
18:40 | <shu> | what are they doing over there |
18:40 | <littledan> | I'd like to understand the implications better here |
18:41 | <rbuckton> | C# is similar, though you also have IEqualityComparer |
18:41 | <littledan> | I mean, how does this differ from keying off an arbitrarily long string? |
18:42 | <littledan> | (as Ashley explained, there are no cycles, and I guess ropes are dags in general too) |
18:42 | <shu> | it's what i was saying, but based on my priors that surely, given complex data, one would take care to figure out a separate key structure so you don't walk your entire data on hash collisions, or you don't walk your entire data to compute the hash |
18:42 | <littledan> | right, agreed |
18:42 | <waldemar> | TCQ shuffling has been having issues today. My topic got deleted twice. I thought that was intentional and didn't want to add it a third time. MAH resurrected it. |
18:42 | <littledan> | but, if people just use one of these things as an immutable data structure and not as a key, what's the problem? |
18:43 | <shu> | oh, because how we implement and optimize the keys use case, which is about shallower DAGs with fewer objects, is very different with deeper DAGs with many objects |
18:43 | <shu> | and i think they're somewhat opposing |
18:43 | <Michael Ficarra> | I think maybe it was on purpose because we were running low on time at the end of that topic. |
18:43 | <shu> | you (littledan) asked for specifics i had in mind other than canonicalization, and i don't at this time |
18:44 | <littledan> | yeah I want to dig into this opposition somehow |
18:44 | <littledan> | like how this relates to long strings |
18:44 | <shu> | let me redirect it back to you, do you think canonicalization by itself isn't sufficiently convincing to make the proposal more inflexible? |
18:46 | <littledan> | I don't quite understand the case for canonicalization. I was wondering about writing a microbenchmark with sets and other affected operations to see how bad it is to add another case to the condition, when it's not taken. |
18:47 | <shu> | it's not just maps and sets, but also all future algorithms and library designs, right? |
18:49 | <shu> | one facet of the "don't overload ===" concern from implementers was diffuse cost that make the feature not "pay as you go". this current direction imagines a future where the message to library authors and stdlib algorithms is, "the new === is === + Composite.equals". that future does not penalize old code, which is great! but that future still does not bottleneck the cost to truly only users of Composites, if the new pattern is adopted at scale |
18:49 | <littledan> | well, I'm having some mental lack of creativity to figure out what future things it will affect. For example, it's not a factor in queues. |
18:49 | <shu> | that's what i'm thinking through. it is still a strictly better situation than the old one, tbc |
18:50 | <shu> | well, neither was === an issue in queues... |
18:50 | <littledan> | I guess in real-world performance, the oldest stuff matters the most |
18:50 | <littledan> | sure, queues is just an example of "I can't think of anything", maybe you can |
18:50 | <shu> | so the case for canonicalization is that it very explicitly bottlenecks the performance to the Composite constructor |
18:51 | <shu> | and seems to be a fine tradeoff to me if we truly believe the keys use case |
18:51 | <Ashley Claymore> | Note: you would only need to walk the entire data on hash collisions if every part of the tree was also a hash collision, as each node would have an individual hash |
18:51 | <bakkot> | yeah but you do need to do that in the "things are equal" case |
18:51 | <bakkot> | which comes up a lot |
18:51 | <shu> | (mark's global communication channel concern notwithstanding, that's a specific technical thing i have no comment on atm) |
18:52 | <nicolo-ribaudo> | With the captioners we are not using regexps on the notes anymore, right? I'm currently replacing manually a lot of "model"s with "module"s |
18:53 | <Ashley Claymore> | yeah, the equals case is always the slowest case. Though you also need to walk the whole thing to canonicalize it. |
18:53 | <ryzokuken> | btw reflector for the next plenary is posted: https://github.com/tc39/Reflector/issues/558 |
18:53 | <Ashley Claymore> | and you could canonicalize under the hood |
18:53 | <shu> | yeah, i'm not saying there is a better algorithm available |
18:53 | <shu> | it's about where that cost shows up |
18:53 | <Ashley Claymore> | yeah. I think it's a great point |
18:53 | <shu> | you can't canonicalize under the hood, that's very visible via object identity, no? |
18:54 | <Ashley Claymore> | I mean internally |
18:54 | <ryzokuken> | along with a link to the sign-up form within which includes some pretty important questions that would help us organize stuff so please check it out and sign-up if you plan to attend in person. |
18:54 | <shu> | not sure what you mean |
18:54 | <Ashley Claymore> | have a seperate pointer |
18:54 | <shu> | ah |
18:54 | <ryzokuken> | we'll add more details over the next few days |
18:54 | <nicolo-ribaudo> | Well ashley I hope for your discussion we didn't have any "model Records", because they have all been Ctrl+H'ed away |
18:55 | <bakkot> | even for the case of keys I am not convinced it makes sense to pay up front |
18:55 | <jschoi> | I did want Records for my data models. |
18:56 | <bakkot> | like emptySet.has(Composite({ x, y, z })) |
18:56 | <littledan> | We told them about this; they should be reflecting that; we should point them to this again and ask them to do better ryzokuken |
18:57 | <bakkot> | many languages have composite keys for maps in some form (often through user-provided hash+equals functions) and I think ~ none of them use canonicalization |
18:57 | <littledan> | can you elaborate on this? |
18:57 | <bakkot> | so if we bill this as composite keys I think users will expect similar performance characteristics to those languages |
18:57 | <shu> | hm, i see. like python's tuples you're thinking of? |
18:57 | <littledan> | are there any particular examples you have in mind? |
18:57 | <bakkot> | or C++ maps |
18:57 | <bakkot> | or Java |
18:57 | <bakkot> | or C# |
18:57 | <shu> | C++ maps have fully hookable everything |
18:58 | <shu> | there's just no need to make that decision at the language level is my understanding |
18:58 | <shu> | but that siad, it's still a signal that popular stdlibs don't provide such functionality |
18:58 | <bakkot> | fair but the normal way I see people using a C++ map is to have hash and equals functions which compute those values on the fly |
18:58 | <bakkot> | and maybe cache the hash in the object, depending |
18:59 | <bakkot> | where "on the fly" means "when the functions are invoked by the map" |
18:59 | <Ashley Claymore> | that's what the polyfill does, computes the hash on the first request for it |
19:00 | <littledan> | it sounds hard GC-wise to deal with canonicalization--how do you decide whether something is still relevant to include in your global table? I guess the values are all WeakRefs and then you sweep it for tombstones? I thought that would have its own cost. |
19:00 | <shu> | yeah, it'd be a weak table you'd have to sweep |
19:00 | <shu> | it has cost in a vaccuum, but it's "just another such table" since this pattern shows up all over the place in v8 |
19:00 | <littledan> | weak by value though, right? |
19:00 | <shu> | and i imagine other engines |
19:00 | <shu> | weak by value, yes |
19:01 | <shu> | but good point on the cost, it ups the barrier of entry |
19:01 | <littledan> | ? Python isn't popular? |
19:02 | <littledan> | I thought Bradley had a whole list of these things |
19:02 | <shu> | wat |
19:02 | <shu> | that was responding to about C++ |
19:02 | <littledan> | Python has composite key functionality, via tuples |
19:03 | <shu> | my view is python's performance culture as an ecosystem is just... very different |
19:03 | <littledan> | oh ok |
19:03 | <shu> | i don't wish to dismiss it out of hand but they deal with performance issues very differently (write c++ libs) |
19:04 | <littledan> | yes but also, we (Bloomberg) are working with others in the Python community on a JIT... |
19:04 | <littledan> | (not PyPy, but rather a less cool one that preserves all the things that make CPython work well in practice) |
19:05 | <shu> | sounds fun |
19:06 | <Michael Ficarra> | I don't like these short days during remote meetings, my work day is pretty much shot anyway, we should just have more meeting time per day and give me back my Thursday |
19:07 | <Ashley Claymore> | I really like the shorter remote plenary days. I don't have your stamina Michael |
19:08 | <littledan> | |
19:08 | <littledan> | it's a case of using a less powerful construct because you don't need that extra power |
19:12 | <jschoi> | JS performance culture in ten years: “Write WASM libs.” |
19:12 | <jschoi> | (This is a joke that I should have put in TDZ.) |
19:12 | <shu> | then we can design the language differently in 10 years |
19:13 | <littledan> | what do you mean? |
19:20 | <jschoi> | Presumably that JavaScript engines deal with performance differently than Python because there is no good recourse for developers that need fast JavaScript. Python has C; JavaScript has WASM. But WASM–JavaScript interoperability is still very early, unlike Python and C, and for the foreseeable future the buck for JavaScript performance stops with JavaScript engines. I am guessing on behalf of Shu. |
19:21 | <eemeli> | I don't like these short days during remote meetings, my work day is pretty much shot anyway, we should just have more meeting time per day and give me back my Thursday |
19:23 | <Michael Ficarra> | We all have to make a sacrifice at some point. The next meeting is at 01:00 to 08:00 for our West coast American friends, which seems a lot worse than working past 22:00 to me. |
19:28 | <jschoi> | Do we not have any notes for the withdrawal of Records/Tuples? |
19:28 | <Ashley Claymore> | @syg am I right in thinking that v8 already needs to load pointers when doing object equality because the pointer tags don't store if the values might be strings? Or am I mixing up the different engine nan tagging schemes |
19:29 | <littledan> | sometimes you have to refresh the google doc |
19:29 | <Ashley Claymore> | @syg am I right in thinking that v8 already needs to load pointers when doing object equality because the pointer tags don't store if the values might be strings? Or am I mixing up the different engine nan tagging schemes |
19:29 | <Ashley Claymore> | Brain trying to at acronyms |
19:57 | <jschoi> | Editors: Should I write the new Array.fromAsync pull request against https://github.com/tc39/ecma262/pull/2942 as it is now, or should I wait until #2942’s conflicts are resolved? |
20:24 | <bakkot> | jschoi we'll talk about it next week, sorry for the lack of guidance |
20:36 | <bakkot> | ljharb Michael Ficarra: let me make the argument a different way. Suppose I have a game and I'm keeping track of points already visited on a 2D grid by storing If we design this feature such that this results in the origin being duplicated in the "has been visited" Set up to three extra times, we have completely abdicated our responsibility as language designers to make the language usable. |
20:45 | <Ashley Claymore> | yeah that was one of the examples in the R&T issue thread (if I can find it). |
20:45 | <Ashley Claymore> | It's a good example of how -0 can easily emerge |
20:48 | <Ashley Claymore> | The "easy fix" to this is that we normalize 0, though this is not pleasing for the cases that want to store the sign |
20:49 | <Ashley Claymore> | Which is why we went with SMZ, it allows the storage but keeps the equality. |
20:52 | <eemeli> | The next TC39 meeting will be the only one this year that's based on a European timezone, and in November we'll be in Japan. The other four meetings will be on North American time, and half again of those are on Pacific time. If we're going to continue having six meetings a year, participation from Europe would be significantly easier if at least the virtual ones were scheduled on US Eastern Time and did not extend later than they currently do, if they don't also rotate globally. |
21:25 | <shu> | for objects there's no additional loads, no: https://source.chromium.org/chromium/chromium/src/+/main:v8/src/codegen/code-stub-assembler.cc;l=15540;drc=3b2367f544f1fbf07f2790c81b02546f73f47467 |
21:31 | <ljharb> | and for your use case and SV, you'd have to check for zero before negating, which is annoying to be sure, and those that want SV would be good. for your use case and SVZ, you're good, but the ones who want SV have no recourse. so i'm not sure why "SVZ" wouldn't be the one designing the language in an unusable way, because it's the difference between "slightly annoying" and "impossible". |
21:32 | <bakkot> | one of these causes innocent developers to have to be aware of -0, one of them doesn't |
21:32 | <bakkot> | -0 is an incredibly niche, specialist thing |
21:32 | <bakkot> | the complexity of handing it should fall on those incredibly niche specialist applications, not on literally everyone else |
21:33 | <bakkot> | also "no recourse" is just straightforwardly false; it is trivial to handle by mapping -0 to some other value before creating your composites |
21:33 | <ljharb> | i agree, when it's possible to handle it. but in this case it's not possible to handle it |
21:33 | <ljharb> | oh hm |
21:33 | <ljharb> | i mean in your game use case yes, that would work |
21:33 | <bakkot> | the game use case should not have to think about -0 at all |
21:33 | <ljharb> | but in a use case where the possible values are "any JS value", it's impossible, because any value needs to be storeable |
21:33 | <bakkot> | no, you make your own value |
21:33 | <bakkot> | let minus_zero = {} |
21:33 | <bakkot> | no one else has that specific value |
21:33 | <bakkot> | done |
21:33 | <ljharb> | they do as soon as i pass around the composite |
21:34 | <ljharb> | and they need that value if they want to pass me one |
21:34 | <bakkot> | you do the mapping at the boundary of your API |
21:34 | <ljharb> | that wouldn't allow them to use the composite the same way i do |
21:34 | <ljharb> | iow it's everyone that needs to be able to do this, not just my api |
21:34 | <ljharb> | (every user of my API, at least) |
21:34 | <bakkot> | I don't understand what that means |
21:35 | <bakkot> | can you give an example? |
21:35 | <ljharb> | i want to give someone a composite like { x: -0 } and have it treated as inequality to { x: 0 } , and for .x to yield -0 when appropriate |
21:35 | <bakkot> | you don't get to decide what equality semantics other people are using |
21:36 | <bakkot> | so this desire confuses me |
21:36 | <ljharb> | hax made a comment about having an "opaque composite"; if that were a thing, then i could make my special -0 sentinel and make a composite for that, and just tell everyone to use that instead of -0 directly. |
21:36 | <ljharb> | what i mean is, i want an application using my library to be able to use the ergonomics of Composite without forcing them to know about "my placeholder for -0" |
21:37 | <ljharb> | which imo is worse than the equally rare game scenario people knowing about actual -0 |
21:37 | <bakkot> | right, so you map -0 to minus_zero when they give you something, and map it back when you give it back |
21:37 | <ljharb> | it's not bad for devs to be aware of things that exist. |
21:37 | <bakkot> | it's bad to force people to deal with -0 if they are not the incredibly niche cases which actually care |
21:40 | <ljharb> | i find your contrived game example pretty niche too tbh |
21:40 | <bakkot> | you find "I want to negate numbers and store pairs of them in a Map" contrived? |
21:40 | <bakkot> | because that's like... a pretty normal thing to happen |
21:41 | <ljharb> | what are some other use cases? |
21:41 | <bakkot> | for... negating numbers? |
21:41 | <ljharb> | for storing pairs of them in a map, and needing to negate those |
21:42 | <bakkot> | it doesn't have to be pairs for this to be relevant, it's just "as a component of some larger thing" |
21:44 | <ljharb> | tbh i'm not convinced that's all that common, people don't really use Maps/Sets at all unless they have object keys. and i'm skeptical naive negation is a common need even when keying on numbers (in any structure). but i'll think more about it |
21:44 | <bakkot> | people will use Maps / Sets a lot more when we have Composites because that is the whole point of them |
21:45 | <bakkot> | they become much more useful when we have Composites |
21:52 | <littledan> | I'm just baffled by the -0 discussion. We spent so long on it previously and arrived at what I thought was accepted as the perfect solution (in terms of semantics people wanted -- maybe not perfect for engines given how it messes up interning) |
21:52 | <littledan> | I argued a lot for what ljharb is now saying, and ljharb argued for treating -0 and 0 as equal! |
21:53 | <littledan> | the use case is the same now as in the previous discussion |
21:58 | <Michael Ficarra> | @littledan I do think that this is a related but different discussion than R&T though |
21:58 | <Michael Ficarra> | with R&T we were talking about how SameValue, strict equality, etc would behave with R&Ts |
21:59 | <Michael Ficarra> | for composites we know how they'll behave: composites have identity and are all inequal to each other |
21:59 | <Michael Ficarra> | the question is instead about how a built-in function compares them, with the function expected to be used as the comparator for Map/Set |
22:00 | <Michael Ficarra> | but crucially not for strict equality generally, Object.is, etc |
22:00 | <littledan> | yes, that's true, so it's all a lower-stakes discussion. but in any case, the use case we're talking about, where the spec uses SameValueZero, coincides. |
22:01 | <Michael Ficarra> | people have got to stop saying the spec uses SameValueZero for Map/Set, I am going to go insane |
22:01 | <Michael Ficarra> | https://matrix.to/#/#tc39-delegates:matrix.org/$5S9AmLOrMkmYVQfILr39ydh4fKIe2B-MeJWzlCRE8R8 |
22:02 | <littledan> | OK yes sorry but that's still the case we're talking about |
22:02 | <littledan> | we still reasoned that, it'd be useful for Maps and Sets to do what's proposed here with respect to this kind of thing |
22:03 | <Michael Ficarra> | yes, if we have composites, we want Map/Set key comparison to be the same thing that Composite.equal does |
22:03 | <Michael Ficarra> | but that's in no way constraining us to use SameValueZero |
22:03 | <Michael Ficarra> | it's constraining us to use either SameValue or SameValueZero |
22:04 | <Michael Ficarra> | and between those two choices, SameValue is better IMO |
22:04 | <bakkot> | Michael Ficarra https://matrix.to/#/!WgJwmjBNZEXhJnXHXw:matrix.org/$y9UQ_IgANImhZBZRwefEUXaCl5pYC8t6YXCpbT51sZU?via=matrix.org&via=mozilla.org&via=igalia.com |
22:04 | <littledan> | it felt previously like we had consensus (until implementer pushback) to use SameValueZero for this case for R&T. Why did that make sense there but not here? |
22:05 | <littledan> | (I can't get these message links to work in my Matrix client) |
22:05 | <Michael Ficarra> | yes yes we can talk about that later |
22:06 | <bakkot> | (sorry, it's a link to my comment with the example with negation) |
22:06 | <Michael Ficarra> | right now, I'm trying to make sure we're on the same page that we're NOT constrained by Map/Set precedent to use SameValueZero and that the equality we're talking about right now is different than what we were talking about for R&T so that discussion also doesn't constrain us |
22:07 | <littledan> | ah, OK, so what changed was that the feeling that Map and Set are bad has expanded to more people and so maybe we want to apply that here, and this would be the case regardless of whether it's R&T vs composites (?) |
22:07 | <Michael Ficarra> | what we are constrained by is not breaking current Map/Set semantics if we want it to use Composite.equals, which means that we must use either SameValue or SameValueZero |
22:08 | <bakkot> | we are not on the same page about this, to be clear |
22:08 | <bakkot> | I hold that we are constrained by Map/Set precedent |
22:08 | <bakkot> | I understand you disagree |
22:09 | <Michael Ficarra> | yes @ljharb pointed out earlier that this was our point of disagreement |
22:09 | <Michael Ficarra> | that there's some sore of pedagogical argument here about 0/-0 |
22:09 | <Michael Ficarra> | and I don't value that as much as I value how difficult and costly it will be to work around SameValueZero |
22:10 | <Michael Ficarra> | "difficult" in terms of engineering effort and "costly" in terms of runtime costs |
22:10 | <bakkot> | well, my main point of disagreement is the thing about exposing -0 insanity to innocent developers, but the Map/Set precedent is sufficient on its own in my mind |
22:11 | <Ashley Claymore> | "difficult" in terms of engineering effort and "costly" in terms of runtime costs |
22:12 | <littledan> | the main thing is, almost everyone will use the default, so we need that to work well in practice |
22:13 | <littledan> | it doesn't really matter what you could implement on top (it matters some, but we also need a good default) |
22:13 | <Michael Ficarra> | that's true, but that's also more likely to be someone with domain knowledge about what they're putting in rather than a library developer trying to create something generically useful |
22:13 | <Michael Ficarra> | so in Kevin's example, that would be a game developer who is using floats knowing that floats have a sign bit |
22:14 | <Michael Ficarra> | that's... not unreasonable to me |
22:14 | <bakkot> | why would they know about -0? |
22:14 | <Michael Ficarra> | they're using floats |
22:14 | <bakkot> | -0 only comes up if you're doing trig or similar |
22:14 | <Michael Ficarra> | or negation? |
22:14 | <bakkot> | and only in weird edge cases even then |
22:14 | <bakkot> | no, I mean, you never have to think about it |
22:15 | <bakkot> | the value arises but you don't have to think about it unless you're doing like atan2 or division by zero or whatever |
22:15 | <Michael Ficarra> | you never have to think about it when doing arithmetic, but you have to think about it when passing it to APIs that take arbitrary values |
22:15 | <Michael Ficarra> | well, most arithmetic |
22:16 | <bakkot> | why? |
22:16 | <bakkot> | I have never thought about it and it has never been a problem |
22:17 | <iain> | FWIW, I have seen this specific pattern while analyzing performance hotspots in SpiderMonkey multiple times, and it's one of the reasons that SM decided to explicitly support this proposal for stage 1. Currently people tend to write x + ":" + y and use string keys, which is Not Great. |
22:17 | <bakkot> | because everything in the language is designed to ensure that remains true |
22:17 | <Ashley Claymore> | Considering: 0 === -0 and [-0].includes(0), I feel like the vast majority of developers will not expect them to not be equal in Composites |
22:18 | <Michael Ficarra> | I think these are poor arguments because they cut the opposite way with NaNs |
22:19 | <Michael Ficarra> | that same person will be surprised about NaN not being found, switch to Object.is , and now zeroes are inequal |
22:19 | <bakkot> | NaN will be found with includes |
22:19 | <Michael Ficarra> | 🙃 |
22:19 | <bakkot> | and with Sets |