jcoo092
2021-10-29 07:59:09

I’m pretty sure that C is, to some extent, usually a wrapper over Fortran too :smile: (since most BLAS/LAPACK implementations are still done in Fortran, and I’m moderately certain Numpy uses BLAS under-the-hood)


cperivol
2021-10-29 09:57:53

I was wondering whether if and friends only consider #f as false or if there may be other falsey objects?


laurent.orseau
2021-10-29 10:01:29

Only #f and #false are false values. This is one of the cleanest things I love about Racket. It makes reasoning easy. (I think I saw some discussion about increasing the set of falsy values, IMO that would be a big mistake)


laurent.orseau
2021-10-29 10:02:11

In particular, 0, #<void> (or (void)), '() are not false values


cperivol
2021-10-29 10:13:05

Thanks!


cperivol
2021-10-29 10:14:11

#f and #false do not refer to the same thing?


laurent.orseau
2021-10-29 10:18:22

They do


markus.pfeiffer
2021-10-29 12:46:39

Cue my olden-days story about the GAP programming language where a boolean can be true, false, or fail (or the even worse story of the value SuPeRfail)


greg
2021-10-29 13:01:10

Open the View menu and choose Show Log.


greg
2021-10-29 13:01:55

The edit control lets you enter a syntax similar to the command line, for what levels of which topics you want to see.


greg
2021-10-29 13:03:51

Oh weird, Slack refreshed very slowly for me. I just replied to them above thinking it was the last message here.


greg
2021-10-29 13:16:13

I mean, punning nil a.k.a. '() to mean “false” is bad. But punning false (#f) to mean “no value” also isn’t wonderful, compared to an option type like “Maybe”, I think? So it seems like they had a good intuition. But I know nothing about GAP and I fully accept your claim that the implementation was horrible. :slightly_smiling_face: (The idea that SuPeRfail means something like “no really! I mean it!! there’s no value!” seems… interesting.)


markus.pfeiffer
2021-10-29 13:18:29

well superfail was the outcome of a not thought through pattern: you pass a function and parameters to a function, and then want to either return the value the function returned or the fact that the execution of the function failed.


laurent.orseau
2021-10-29 13:24:58

Apart from the quality of the implementation, the name itself seems a terrible choice


laurent.orseau
2021-10-29 13:25:39

“If the stack overflows, let’s call this Megafail!”


markus.pfeiffer
2021-10-29 13:38:07

what happens if the function you passed into your function returns superfail itself tho


soegaard2
2021-10-29 13:40:48

There are quite a few BLAS/LAPACK implementations. So many it can be confusing.

The original in Fortran (which can be compiled, so it can be called from C). A version that stems from running a C->Fortran translator in the original implementation.

And a lot of reimplementations. One is made by Intel. Some suggest that implementation runs slowly on AMD-processors!


soegaard2
2021-10-29 13:41:53

@markus.pfeiffer GAP? The one used make group calculations?


laurent.orseau
2021-10-29 13:42:05

@markus.pfeiffer That one is easy, it’s a supersuperfail of course


sorawee
2021-10-29 17:09:48

> The registration will open around the end of November. FYI


ben.knoble
2021-10-29 17:16:17

Thanks so much!


markus.pfeiffer
2021-10-29 17:20:00

@soegaard2 yep


ben.knoble
2021-10-29 17:23:33

An interesting macrology question based on toying with Beautiful Racket (not my question): Why does this code: (define-macro-cases bf-op [(bf-op ">") #'(set! ptr (add1 ptr))] [(bf-op "<") #'(set! ptr (sub1 ptr))] [(bf-op "+") #'(set-current-byte! (add1 (current-byte)))] [(bf-op "-") #'(set-current-byte! (sub1 (current-byte)))] [(bf-op ".") #'(write-byte (current-byte))] [(bf-op ",") #'(set-current-byte! (read-byte))]) (provide bf-op) (define arr (make-vector 30000 0)) (define ptr 0) (define (current-byte) (vector-ref arr ptr)) (define (set-current-byte! val) (vector-set! arr ptr val)) …yield this error: expander.rkt:21:23: set!: cannot mutate module-required identifier at: ptr in: (set! ptr (add1 ptr)) location...: expander.rkt:21:23 (line 21 in the error is line 2 above) …but this code: (define-macro-cases bf-op [(bf-op ">") #'(update-pointer add1)] [(bf-op "<") #'(update-pointer sub1)] [(bf-op "+") #'(set-current-byte! (add1 (current-byte)))] [(bf-op "-") #'(set-current-byte! (sub1 (current-byte)))] [(bf-op ".") #'(write-byte (current-byte))] [(bf-op ",") #'(set-current-byte! (read-byte))]) (provide bf-op) (define arr (make-vector 30000 0)) (define ptr 0) (define (current-byte) (vector-ref arr ptr)) (define (set-current-byte! val) (vector-set! arr ptr val)) (define (update-pointer f) (set! ptr (f ptr))) (i.e. with the set! call pulled out to a helper function) …work fine? Does define-macro-cases not allow you to have a set! call in the top-level expansion yet allow it one level indirected?


samth
2021-10-29 17:26:06

This isn’t a macro-related restriction — all set! of a variable must be in the module that it’s defined in, and macros don’t let you circumvent that.


ben.knoble
2021-10-29 17:30:20

Well, the level of indirection vs. expansion does sort of confuse the issue, esp. to a beginner. My comment was something like > I can’t quite trace it all the way through, but I think the issue is that the version that expands without set! directly is acceptable because of hygiene (the set! call still lives in the module as the value). But in the other version, the set! shows up in a module while ptr is still (syntactically, because hygiene) a reference to a value from a different module? Is that even close to right?

The error message doesn’t really help here, since it’s not obvious how ptr is module-required (esp. to a beginner).


samth
2021-10-29 17:30:41

no, there’s no relation to hygiene


samth
2021-10-29 17:31:38

but the broader point is right — when you expand the macro-version, the set! goes in the other file


samth
2021-10-29 17:31:42

and that’s not allowed


badkins
2021-10-29 17:33:03

If I understand correctly (not my question either, a user in our local slack), they aren’t explicitly requiring the module that has the identifier being complained about. Is there something about the macro expansion that implicitly requires the module, and thus, produces the error about a “module-required identifier” ?


ben.knoble
2021-10-29 17:35:06

^that’s where I drug hygiene in: the identifier isn’t even exported, so I assumed the ability to reference it in the expanded module had something to do with hygiene


ben.knoble
2021-10-29 17:35:31

(I’m assuming it isn’t provided, anyway)


badkins
2021-10-29 17:35:53

I asked for more info in our other slack :)


ben.knoble
2021-10-29 17:36:11

saw that, my follow-up clarified my assumption there


samth
2021-10-29 17:38:55

well, whether that has to do with hygiene sort of depends on what you mean by hygiene, but the check doesn’t have anything to do with whether something is required or not


badkins
2021-10-29 17:39:56

The error message is: “expander.rkt:21:23: set!: cannot mutate module-required identifier” which does seem to indicate require is relevant.


samth
2021-10-29 17:40:32

I understand that that’s the error message but it doesn’t have anything to do with require


badkins
2021-10-29 17:40:52

I guess I don’t understand what a “module-required” identifier is.


samth
2021-10-29 17:42:06

I think that error message means “identifier from another module” but it is not a good error message


badkins
2021-10-29 17:42:44

Ah. Yes, I like your error message better :)


badkins
2021-10-29 17:45:58

For any json users, is there any reason why a hash with string? keys should not be a jsexpr? ? In other words, unless I’m missing something, it seems both lines below should return #t: (require json) (jsexpr? (hash "foo" "bar")) ; => #f (jsexpr? (hash 'foo "bar")) ; => #t In the context of a web app, field names will typically be identified with strings, so having to convert between symbols and strings seems like an unnecessary hassle.


djholtby
2021-10-29 17:51:46

The prescriptivist reason is that that’s how the module defines the data type


djholtby
2021-10-29 17:52:27

Strings are mutable so it’s best to avoid using them as keys. Also hasheq is more efficient than hash


badkins
2021-10-29 17:55:05

I’m not sure how that applies here. I’m not asking whether or not one should use strings as keys in a hash. Assuming you do have a hash with string keys, why can’t you use it in jsexpr->string ?


badkins
2021-10-29 17:55:50

Or, in other words, what disadvantage is there to allowing that to happen?


badkins
2021-10-29 17:58:32

I’m pretty sure jsexpr->string is going to call symbol->string when producing the output.


djholtby
2021-10-29 18:00:11

Those are the reasons that the data type is restricted to symbols. The jsexpr->string could certainly be more broad, but it isn’t.


djholtby
2021-10-29 18:02:54

(I’m not responsible for the package, I just use it)


greg
2021-10-29 18:12:21

The “keys must be symbols” constraint is helpful (I think) for functions like read-json that produce something you need to process, and jsexpr? is the (stricter) contract there. Given that, it makes sense for something like jsexpr->string to take, you know, a jsexpr?. :slightly_smiling_face:

I think maybe you (or even the jsexpr package) could define a wrapper function that takes a hash-table with string? keys, converts them, and calls jsexpr->string. It can have a looser contract.


greg
2021-10-29 18:12:50

Maybe someone even wants the keys to be any/c, and does ~a and string->symbol on them to make symbol keys.


greg
2021-10-29 18:13:10

So I think the question of how “loose” to go the other way, maybe is fine to leave up to each user of the package?


greg
2021-10-29 18:13:29

At least that’s how I’d defend it if I were paid to. :slightly_smiling_face:



sorawee
2021-10-29 18:17:19

The PR authors no longer use Racket though. So unless someone wants to take it over, it probably won’t get merged


badkins
2021-10-29 18:24:07

Reading JSON is an entirely different thing. I still see zero reasons to force a user of json to convert a key from a string to a symbol, just to have jsexpr->string convert the symbol back to a string.


badkins
2021-10-29 18:24:33

I’m not saying there are no reasons, just none articulated yet.


ryanc
2021-10-29 18:25:41

One argument against allowing string keys is to avoid having to consider how things like (jsexpr->string (hash 'a 1 "a" 2 (string #\a) 3)) should behave.


badkins
2021-10-29 18:26:57

Wouldn’t that simply result in the following JSON string? { "a" : 1, "a" : 2, "a" : 3 }


ryanc
2021-10-29 18:27:28

IMO, that would be bad.


badkins
2021-10-29 18:28:07

Yeah, I typed in haste. I assume you’re implying the json module has some validation along these lines.


badkins
2021-10-29 18:29:05

According to my Chrome javascript console, attempting to create the object { "a" : 1, "a" : 2 } results in { "a" : 2 }


badkins
2021-10-29 18:29:32

So your example would end up as { "a" : 3 }


ryanc
2021-10-29 18:30:09

My point is that with symbol keys, you don’t even have to do validation. (Really, jsexpr should be restricted to interned symbols, and I’m not sure that is enforced.)


samth
2021-10-29 18:30:25

That’s a property of JS syntax, not of the JSON printer, though


samth
2021-10-29 18:31:06

What you wrote is the equivalent of #hash((a . 1) (a . 1))


badkins
2021-10-29 18:31:14

(jsexpr? (hash 'foo "bar" 'foo "foo")) => #t


samth
2021-10-29 18:31:34

that only has one entry, though


samth
2021-10-29 18:32:50

The hash @ryanc mentioned has 3 entries


badkins
2021-10-29 18:33:40

JavaScript evaluates left to right, so I still think the result would be { "a" : 3 }


samth
2021-10-29 18:34:04

no, that’s not relevant


badkins
2021-10-29 18:34:06

Except Racket probably doesn’t preserve order here … :(


samth
2021-10-29 18:34:34

{"a":3, "a":2} is not valid JSON


badkins
2021-10-29 18:34:43

Ok, thanks @ryanc - I accept your disadvantage :)


badkins
2021-10-29 18:35:44

Rails has something like HashWithIndifferentAccess which is kind of horrible.


ryanc
2021-10-29 18:39:02

IIUC, it is valid, but the JSON spec just shrugs at the question of what duplicate keys should mean.


badkins
2021-10-29 18:40:53

I suppose I could change: (define (form-values req) (for/hash ([ b (in-list (request-bindings/raw req)) ]) (cond [ (binding:form? b) (values (bytes->string/utf-8 (binding-id b) #\space) (bytes->string/utf-8 (binding:form-value b) #\space)) ] [ (binding:file? b) (values (bytes->string/utf-8 (binding-id b) #\space) (binding:file-content b)) ]))) to use symbols, but I’ll need to ponder that for a while. The keys are coming in as strings (essentially) from HTTP, and strings seem to be a reasonable choice for the keys in this case. The pathological case above seems a bit contrived.


badkins
2021-10-29 18:46:00

@popa.bogdanp do you convert form values to a hash with symbol keys?


joel
2021-10-29 19:47:32

Following


badkins
2021-10-29 20:02:36

My current project is new, and not huge yet, so I just changed the above code to: (define (form-values req) (for/hash ([ b (in-list (request-bindings/raw req)) ]) (cond [ (binding:form? b) (values (string->symbol (bytes->string/utf-8 (binding-id b) #\space)) (bytes->string/utf-8 (binding:form-value b) #\space)) ] [ (binding:file? b) (values (string->symbol (bytes->string/utf-8 (binding-id b) #\space)) (binding:file-content b)) ]))) and fixed-up the rest of the code to match, and so far, so good :) I think I’ll stick with symbol keys for now.


badkins
2021-10-29 20:03:49

Using symbols everywhere avoids the madness of Rails’ HashWithIndifferentAccess


greg
2021-10-29 21:10:12

That looks good to me. In fact ISTR writing a little bytes->symbol function composing those two and using it in situations just like this.


sschwarzer
2021-10-29 22:53:30

Creating color maps isn’t trivial. I recommend not using the rainbow color map. :slightly_smiling_face:

Here are a few links that I find interesting: https://www.kennethmoreland.com/color-advice/BadColorMaps.pdf https://www.kennethmoreland.com/color-advice/ https://www.kennethmoreland.com/color-maps/


notjack
2021-10-29 23:54:38

where does that message come from? I’d like to change it


badkins
2021-10-30 00:43:30

This is so much better now :) I’m glad the group talked me down from heading down the “using both symbols and strings with hashes” road :) Nothing to remember now - it’s always a symbol.


alexharsanyi
2021-10-30 03:06:31

The color maps defined in the colormaps package are not mine, but sourced from different places. The rainbow one comes from here: https://personal.sron.nl/~pault/, I will have a read of the website you linked to, and see if I can extend the package with additional color maps.


philip.mcgrath
2021-10-30 05:32:00

I’ve done this with a “server” that I start via system* or similar and just talk to over standard IO in JSON or something, without any HTTP or whatever.