Stream: ideas

Topic: `and` and `or` keywords for binary operators


view this post on Zulip Sam Mohr (Jan 17 2025 at 03:11):

I repeat the or and and suggestion

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:11):

That would fix this

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:11):

Yeah I agree that's viable @Sam Mohr

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:11):

I actually like that. I think even Zig does that right?

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:12):

Here's the kind of example I'm worried about:

foo = |args|
    abc!
    || xyz

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:12):

That's what we had to add a test case for

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:12):

If that || were indented by a single extra space, then it's all the sudden an operator

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:12):

I think it should have to be a full INDENT

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:12):

None of the rest of the parser requires that

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:13):

I know

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:13):

hm, or and and are interesting in this context :thinking:

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:13):

it's a bit of strangeness budget but pretty minor

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:13):

But when we move to token-based parsing, having just INDENT and DEDENT tokens to parse is nice

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:13):

or maybe like...unusual-ness budget?

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:13):

they're not exactly alien choices haha

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:14):

There is a few well known languages with this

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:14):

yeah

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:14):

Python is the big one of course

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:14):

Python, Zig, Elixir...

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:14):

That's fighting for #1 language these days

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:14):

I'm sure I can think of more

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:15):

yeah that's what I mean by like "unusual rather than strange"

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:15):

I think it would be more popular if not for C copying everywhere

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:15):

most mainstream languages don't do it, but some do

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:16):

the thing I dislike about it is that it means you can't use those words in DSLs because they have to become reserved keywords

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:16):

but on the other hand, a thing I like about it is that except for historical reasons it's kind of silly to have && and || but not & and |

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:16):

I think a total beginner to programming would understand or way faster than "it's like || which is two pipes because | meant bitwise originally"

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:17):

yeah that's definitely true haha

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:17):

the thing I dislike about it is that it means you can't use those words in DSLs because they have to become reserved keywords

What if they were operator overload-able? :P

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:17):

That'd work for me

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:17):

Wait

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:17):

Short circuiting breaks

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:18):

AND/OR is used in

CoffeeScript, Common Lisp, Emacs Lisp, Io, Logo, Lua, Modula-2, Perl, Perl6, PHP, Pliant, Python, Ruby, Scheme, Smalltalk

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:18):

A few really popular languages in there

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:18):

CoffeeScript has both if I remember right

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:18):

Unless we can do something wacky where boolean short-circuits but nothing else does

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:18):

I think maybe Ruby too?

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:18):

Short circuiting breaks

Does it? I think it just means the signature of the function that implements it needs to be a bit funky.

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:19):

Could you give a signature?

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:19):

image.png

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:20):

I don't think allowing it to be overloadable is a good idea

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:20):

that sounds like a huge footgun

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:20):

That sounds like Haskell

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:20):

but I do think it's pretty rare to use them in DSLs

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:20):

Are the griffons gonna come save us from mount syntax?

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:20):

I'm sorry Smalltalk

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:21):

I don't think allowing it to be overloadable is a good idea

Yeah, I kinda agree. For completeness tho, I was thinking along these lines:

and : (t, ()->t) -> t

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:22):

seems worth a separate thread to gather feedback, but I'm generally open to the idea of and and or keywords replacing && and ||

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:23):

also, we could continue to parse the current ones (maybe just ignoring the edge case) and have the formatter quietly turn them into and and || for you

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:23):

and have the compiler warn if they're used as binops

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:23):

Yeah I was thinking exactly the same thing

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:23):

because a lot of beginners will trip over that out of habit

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:23):

(coming from other languages)

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:23):

{-# LANGUAGE BrokeYourShortCircuitingOperators #-}

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:24):

Hey, nowhere did I suggest breaking short circuiting!

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:24):

I know, sorry, I'm on a tear with the breaking short circuiting jokes, and it's past my bed time

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:24):

Haha np

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:25):

Also, I have to dig at Haskell every opportunity I get

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:25):

Because I'm not smart enough to write a White Paper

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:28):

same

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:28):

Or read zero point style

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:29):

I'm just a Monoid that's NOT in the category of endofunctors

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:29):

I haven't fact-checked this, but here's what perplexity.ai says:

Languages using "&&" and "||"

  1. C
  2. C++
  3. Java
  4. JavaScript
  5. C#
  6. PHP
  7. Swift
  8. Go
  9. Kotlin
  10. TypeScript
  11. Rust

Languages using "and" and "or"

  1. Python
  2. Ruby
  3. Lua

Languages supporting both "&&"/"||" and "and"/"or"

  1. Perl
  2. R

Languages with unique operators

  1. MATLAB (uses "&" and "|" for element-wise operations, "&&" and "||" for short-circuit operations)
  2. Visual Basic (.NET) (uses "And" and "Or" for bitwise operations, "AndAlso" and "OrElse" for short-circuit operations)
  3. SQL (uses "AND" and "OR" keywords)
  4. Haskell (uses "&&" and "||" for boolean operations, but also has "and" and "or" functions for lists)

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:29):

Also include PHP in the "and" and "or" category

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:29):

it supports both?

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:30):

oh this is interesting rationale: https://github.com/ziglang/zig/issues/272 (although we have ? for control flow, so we don't follow that convention anyway)

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:30):

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:30):

We have been having some parsing troubles in the interaction of our new |args| body function syntax and our || or binary operator syntax. Namely, || is both a list of zero arguments and also the "or" operator. To avoid having to require indentation when we see binary operators at the start of a line, why don't we instead switch to and and or for binary operators?

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:31):

Collecting arguments from other threads.

Pros:

Cons:

Possible mitigations:

view this post on Zulip Notification Bot (Jan 17 2025 at 03:31):

67 messages were moved here from #ideas > zero-arg functions & sugar by Sam Mohr.

view this post on Zulip Anthony Bullard (Jan 17 2025 at 03:32):

Richard Feldman said:

oh this is interesting rationale: https://github.com/ziglang/zig/issues/272 (although we have ? for control flow, so we don't follow that convention anyway)

I was arguing for a Zig style keyword for this. I actually loved that style when I was on my Zig arc

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:33):

The other contender here is not. Do we want to change !is_admin(user) to not is_admin(user)?

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:33):

feels like that will create more parens

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:33):

I'd say yes for consistency, as that one can be operator overloaded pretty easily

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:33):

I'm not sure if it will

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:34):

oh maybe not nm

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:34):

:thinking: we could consider .not()

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:34):

Yep

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:35):

would we keep != at that point?

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:35):

Python does that

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:35):

So, not (hah!) that weird

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:35):

it's kinda funny that right now you can have !foo!()

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:35):

Actually, removing != means that you don't need to have == and != impls for custom types

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:36):

just a single .equals() method

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:36):

I don't think we want to remove !=

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:37):

The problem is when we lose efficiency because of this, but that's pretty minor

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:37):

either rename or keep as-is

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:38):

I dunno, ! feels nicer to me than not

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:39):

it's more concise, doesn't reserve a keyword, is easily understood

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:39):

has symmetry with !=

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:39):

I think we should keep that one as-is

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:39):

A discussion on this from only 4 months ago: #ideas > `not` keyword instead of `!` prefix @ 💬

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:39):

Same conclusion

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:40):

It has symmetry of !condition and x != y

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:40):

oh yeah I forgot about this point:

Richard Feldman said:

I don't have strong feelings about not vs ! but I do appreciate that if we're making ! mean "an effect is happening here" that it makes it even easier to scan a chunk of code for effects if that is the only thing that ! means

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:40):

good point, Past Me

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:40):

hmmm

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:41):

We'd have to pick a != equivalent we'd even consider, then

view this post on Zulip Sam Mohr (Jan 17 2025 at 03:41):

Or of course, get rid of !=

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:42):

Ayaz Hafiz said:

I always find not super annoying in Python
because != and = exist but not ! and sometimes i forget because in other languages it's available
keeping != seems like a good idea too. i mean even sql added != because it was more familiar than <>

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:43):

a consistent theme in that thread is very strong support for != as the "not equals" operator

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:43):

and if we have that, then we can't have "! only means effectful function"

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:44):

at which point I'd agree with More Recent Past Me on this:

Richard Feldman said:

it's more concise, doesn't reserve a keyword, is easily understood
has symmetry with !=

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:45):

although

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:45):

I guess a counterargument is that != would never appear touching a letter (in practice)

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:45):

so foo! would always stand out as a separate token from !=

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:46):

plus they would be syntax-highlighted differently because one is part of a name and the other is an operator

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:47):

so maybe it's fine if ! is only for effectful function names and !=

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:47):

in terms of scannability

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:47):

(although status quo feels fine there too, heh)

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:48):

Is a not= b so terrible?

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:49):

Actually I think I answered my own question

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:49):

That does look terrible

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:49):

I've been playing with different samples from various repos... and they all look fine to me. Here's an example.

is_hex : U8 -> Bool
is_hex = |b|
    (b >= '0' and b <= '9')
    or (b >= 'a' and b <= 'f')
    or (b >= 'A' and b <= 'F')

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:50):

I second Sam's argument that this is more beginner friendly

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:51):

We could always do the same thing with !foo and _parse_ it but format it as not foo

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:52):

I don't love the idea of using not though...

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:52):

Maybe I've just been doing too much python, but... "that's what python does" is a reasonably strong argument in my book

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:53):

That said, IIRC that did get a bit of getting used to when I first learned python

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:53):

Particularly not vs != was a bit confusing

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:53):

expect not is_hex('g')
expect not is_hex('\\')
expect not is_hex('-')

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:54):

Imagine this in the context of effectful functions

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:55):

expect !foo!()

vs

expect not foo!()

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:55):

Honestly I think the not is a lot more readable in that situation

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:55):

Too many !s going on

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:55):

effectful functions that return booleans are pretty rare though

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:55):

We would encourage Tags though for roc...

check_file! : Str => Result [Good, Bad] [IOError]
check_file! = |str|
    if str == "good" then
        Ok(Good)
    else if str == "bad" then
        Ok(Bad)
    else
        Err(IOError)

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:56):

the only common one I can think of is !File.exists!(path) but actually I think that's kind of a counterexample, in that usually if you're doing something like "if it doesn't exist, then create it" you're leaving performance on the table compared to attempting to create it and then ignoring any "it already exists" errors

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:57):

(2 syscalls vs 1)

view this post on Zulip Luke Boswell (Jan 17 2025 at 03:57):

expect is_hex('A') and not is_hex('g') or is_hex('0')

I think not is growing on me... but I want to keep!= and == is that rational?

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:58):

it's what Python does

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:58):

is_internet_connected!()

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:58):

I think we should decouple the not discussion from the and and or discussion

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:58):

and and or solve a problem with lambda syntax

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:59):

not is stylistic only

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:59):

If we switch to and and or, I'd argue we should at least _parse_ not and turn it into !

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:59):

Those three often go together

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:59):

that would make it effectively a reserved keyword

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:59):

Yes

view this post on Zulip Joshua Warner (Jan 17 2025 at 03:59):

Well, mostly

view this post on Zulip Richard Feldman (Jan 17 2025 at 03:59):

haha

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:00):

We can parse most constructs just fine, especially if we don't support WSA anymore

view this post on Zulip Richard Feldman (Jan 17 2025 at 04:00):

I don't think we should reserve a keyword and then not use it for anything semantically :big_smile:

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:01):

In fact - in a non-WSA world, not doesn't have to be reserved at all in order to parse not foo

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:01):

You could have a function called not() just fine, for example. You could also define that function without issue. Or have an arg with that name, etc.

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:03):

I don't think we should reserve a keyword and then not use it for anything semantically

FWIW C++ does exactly this with and / or (and I think not?)

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:04):

Most people use && / ||, but you can also do and / or and it means the same thing

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:04):

Not that c++ is a shining example of a language

view this post on Zulip Richard Feldman (Jan 17 2025 at 04:07):

yeah fair point about the space having different meaning

view this post on Zulip Richard Feldman (Jan 17 2025 at 04:08):

at any rate, are there any concerns/objections about switching to and and or?

view this post on Zulip Richard Feldman (Jan 17 2025 at 04:09):

seems like the general sentiment so far has been neutral to positive

view this post on Zulip Richard Feldman (Jan 17 2025 at 04:09):

but that may just be because the alternative perspective hasn't been voiced in the thread yet :big_smile:

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:11):

I think the main concern I heard was that you can't name things like that e.g. for a dsl

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:11):

With some very slight caveats tho I think that can actually work out fine as a non-reserved keyword

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:12):

For example:

and = |a, b| build_and_node(a, b)
and(1, 2)

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:13):

In both of those cases, we just need a lookahead of 1 "token" (even tho the parser doesn't use those now!) to know that those can't possibly be operators

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:13):

Actually no I take that back

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:13):

That could be parsed as:

and = |a, b| build_and_node(a, b) and (1, 2)

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:14):

That seems like it shouldn't parse that way, though I believe you that it would today

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:15):

If the function body starts on the same line as the args, we shouldn't parse more statements

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:15):

Unless they have at least 1 space of indent

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:15):

Ahh true; that's not ambiguous in that particular case

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:16):

a + b
and(1, 2)

... is ambiguous in that way tho

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:16):

Or, more properly,

foo!()
and(1, 2)

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:17):

We could keep the current rule where we're very particular about whitespace between the function and the parens

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:18):

e.g. so if you actually wanted the and operator you'd have to write:

a + b
and (1, 2)

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:18):

That feels fragile tho, particularly if that's the only place we need that constraint

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:20):

I'd vote for making them reserved keywords

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:20):

We can always relax that in the future

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:21):

It works as a method, though

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:21):

Only at the start of an expression

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:22):

Otherwise it's almost-but-not-technically ambiguous

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:22):

You could do (and(1, 2)) with zero ambiguity, or 1 + and(1, 2)

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:26):

Oh, I meant with the dot in the front

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:27):

Which is most of the usage for methods

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:27):

Ah interesting

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:28):

I was imagining a dsl for building up z3 expression

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:28):

I'd expect left.and(right) in SD Roc

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:28):

Ahh, true that works

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:29):

I was imagining it as a function

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:29):

It'd be weird if that was the one example of something you _had_ to call via SD

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:29):

Which means we don't want it as a reserved keyword, unless methods get exempt from that keyword collision check

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:29):

Err, I would still vote to make it reserved

view this post on Zulip Sam Mohr (Jan 17 2025 at 04:30):

Pretty sure that's how we'll check for SD types

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:30):

My dsl can be andz(1, 2) instead and it's not terrible

view this post on Zulip Joshua Warner (Jan 17 2025 at 04:31):

What I _would_ love for such a DSL is operator overloading :P

view this post on Zulip Kilian Vounckx (Jan 17 2025 at 07:39):

Just some trivia
c++ allows both '&&' and '||', as well as 'and' and 'or'

Even c apparently has the <iso646.h> header which defines macros to turn the keywords into operators. It was used historically for users with keyboards that didn't have the symbols

view this post on Zulip Kilian Vounckx (Jan 17 2025 at 07:39):

0a6976e7-25e9-49af-b5d6-cf0a1ce7aae3.png

view this post on Zulip Kilian Vounckx (Jan 17 2025 at 07:40):

Here is a full list in the c header

view this post on Zulip Anthony Bullard (Jan 17 2025 at 10:43):

I’ll just say this. People who put a space between the function and the arguments in PNC have questionable motives. I’m coming at you GNU

view this post on Zulip Norbert Hajagos (Jan 17 2025 at 15:49):

Anthony Bullard said:

I’ll just say this. People who put a space between the function and the arguments in PNC have questionable motives. I’m coming at you GNU

Yeah, I don't trust them too :big_smile:

I like the and and or keywords. They seem beginner friendly. Always perceived them friendly, as in kind and welcoming (syntax is so much about vibes).
I'm unsure aboutnot. It seems wrong to see two keywords after eachother like thing and not other_thing. Different syntax highlighting would help, but there's no such problem with !. There is just something clear about ! coming right before the operand, without a space. A solution to this particular problem would be thing and other_thing.not(), which brings the opearnd (in this case argument) together with the not operator. If that's the style that will be mainstream, that will look even more weird to outsiders than combining and, or and !. It also doesn't help that thing.not() reads backwards compared to how you would think about it in English.

view this post on Zulip jan kili (Jan 17 2025 at 19:13):

Richard Feldman said:

it's kinda funny that right now you can have !foo!()

Coming soon: ¿por_qué!?

view this post on Zulip jan kili (Jan 17 2025 at 19:16):

I have a selfish two thumbs up (👍 and 👍) for replacing symbolic operators with reserved keywords words in general, and especially these two. (since today I'm mostly writing scripts that prioritize readability to a non-technical audience)

view this post on Zulip Sam Mohr (Jan 17 2025 at 21:34):

Bool.and and Bool.or mean that we can't make these operators reserved keywords, I think

view this post on Zulip Sam Mohr (Jan 17 2025 at 21:36):

I did something funky for Result.try where we parse the word "try" as its own AST node, and if it doesn't desugar to a LowLevelTry, then we convert it back to the word "try"

view this post on Zulip Sam Mohr (Jan 17 2025 at 21:36):

We could try do the same thing here?

view this post on Zulip Richard Feldman (Jan 17 2025 at 22:13):

Sam Mohr said:

Bool.and and Bool.or mean that we can't make these operators reserved keywords, I think

we can just remove those

view this post on Zulip Richard Feldman (Jan 17 2025 at 22:24):

I think now that we do short-circuiting, it's probably a bit confusing to have them (for use in pipelines) because they don't short-circuit

view this post on Zulip Sam Mohr (Jan 17 2025 at 22:26):

Oh, that's fair

view this post on Zulip Sam Mohr (Jan 17 2025 at 22:26):

I was trying to do it in spite of what you said in case I could make it work somehow

view this post on Zulip Sam Mohr (Jan 17 2025 at 22:26):

But if they don't short circuit, that's a problem

view this post on Zulip Richard Feldman (Jan 17 2025 at 22:39):

yeah, the footgun aspect makes me think whatever convenience they offer isn't worth it

view this post on Zulip Sky Rose (Jan 18 2025 at 04:30):

If we lose Bool.and, we lose the ability to use .and() in static dispatch. (Which is probably fine, but worth saying we're okay with it.)

view this post on Zulip Sky Rose (Jan 18 2025 at 04:32):

(deleted)

view this post on Zulip Sam Mohr (Jan 18 2025 at 04:34):

If methods are allowed to have keyword names, then that restriction could go away

view this post on Zulip Sam Mohr (Jan 18 2025 at 04:35):

Which still is a restriction since it means you can't call the method like a normal function

view this post on Zulip Sam Mohr (Jan 18 2025 at 04:35):

But that seems minor to me

view this post on Zulip Sky Rose (Jan 18 2025 at 04:51):

Oh I wonder if you could also refer to the function if it was qualified Bool.and. Like as long as it's got a dot before it you know it's the function not the keyword

view this post on Zulip Brendan Hansknecht (Jan 18 2025 at 04:53):

I feel like that is something not worth worrying about yet. I think direct use of Bool.and is exceptionally rare and it is a pretty minimal cost to have to type |a,b| a and b

view this post on Zulip Brendan Hansknecht (Jan 18 2025 at 04:54):

Probably less common in roc cause using Bool is so rare when tags are so easy and promoted in general.

view this post on Zulip Richard Feldman (Jan 18 2025 at 05:00):

Sky Rose said:

If we lose Bool.and, we lose the ability to use .and() in static dispatch. (Which is probably fine, but worth saying we're okay with it.)

I think this is good though - if it's a function (that takes two non-functions for arguments) then it's not short-circuiting and is error-prone

view this post on Zulip Richard Feldman (Jan 18 2025 at 05:00):

I think we're better off not having it

view this post on Zulip Sam Mohr (Jan 18 2025 at 05:01):

Bool.and in particular we shouldn't keep, yes. But would it be bad to have .and() available for DSLs?

view this post on Zulip Sam Mohr (Jan 18 2025 at 05:02):

Yes, we don't need to worry about this yet

view this post on Zulip Richard Feldman (Jan 18 2025 at 05:02):

yeah I think we can think about that later

view this post on Zulip Richard Feldman (Jan 18 2025 at 05:02):

it's obviously not blocking any DSLs since you can just add a letter as a workaround :big_smile:

view this post on Zulip shua (Jan 22 2025 at 08:38):

for some other point, I know lean has some equivalent functions between functions that return Prop and functions that return bool. The latter usually get a b prefix, so eg eq for Prop and beq for bool. We could do the same with Bool.band and Bool.bor. Not exactly aesthetic.

Alternatively, And and Or are traits in rust, so overloading the trait overloads the meaning of a && b, and I've used that and BitAnd in some rust dsls to get nice and-y or-y syntax.


Last updated: Jun 16 2026 at 16:19 UTC