Stream: beginners

Topic: ✔ How to fix Dict type?


view this post on Zulip Jason Hobbs (Dec 04 2023 at 19:02):

I've tried to be very explicit for the compiler, with hints to use (Int Unsigned32), and have even added a bunch of Num.toU32 throughout my code. Yet, it's still finding an issue. I'm not sure how to continue debugging this.

The very odd thing to me is this fixes it.

copies = 0

This breaks the Dict type:

copies = Dict.get numCardsByGame index |> Result.withDefault 0

Error message:

This 2nd argument to |> has an unexpected type:

51│                      |> incrementCards numCardsByGame
                                           ^^^^^^^^^^^^^^

This numCardsByGame value is a:

    Dict (Int Natural) (Int Natural)

But |> needs its 2nd argument to be:

    Dict (Int Unsigned32) (Int Unsigned32)

The full code section:

AoC code inside

view this post on Zulip Jason Hobbs (Dec 04 2023 at 19:14):

Ah, I see... It's that the copies variable needs to be Int Natural given how it's used later. Then, following that backwards, we see that Dict.get numCardsByGame index... must be able to return a Int Natural.

view this post on Zulip Notification Bot (Dec 04 2023 at 19:14):

Jason Hobbs has marked this topic as resolved.

view this post on Zulip Notification Bot (Dec 04 2023 at 19:16):

Jason Hobbs has marked this topic as unresolved.

view this post on Zulip Jason Hobbs (Dec 04 2023 at 19:17):

I think my understanding about "following that backwards" is wrong.

Appending |> Num.toNat to the Dict.get should've resolved the need for Dict.get to return an Int Natural. Especially, since I gave it the starting type emptyDict : Dict (Int Unsigned32) (Int Unsigned32)

view this post on Zulip Jason Hobbs (Dec 04 2023 at 19:21):

Okay, that did resolve half of it... I just didn't realize the same thing was happening via the index I was using.

Got there...

                copies : Nat
                copies = Dict.get numCardsByGame (Num.toU32 index) |> Result.withDefault 0 |> Num.toNat

view this post on Zulip Notification Bot (Dec 04 2023 at 19:21):

Jason Hobbs has marked this topic as resolved.

view this post on Zulip Brendan Hansknecht (Dec 04 2023 at 19:27):

the fun of integer types.... Nat being an especially common pain point due to suddenly changing the api and leading to type mismatch.

view this post on Zulip Jason Hobbs (Dec 04 2023 at 19:45):

Yeah, I don't really know how to troubleshoot these very well yet.

Right now, it's a lot of trial and error toggling compiler hints and casting inline to get more info.

view this post on Zulip Brendan Hansknecht (Dec 04 2023 at 19:47):

Probably a sign that our errors aren't great here due to unifying wrong and then they type getting caught elsewhere

view this post on Zulip Brendan Hansknecht (Dec 04 2023 at 19:48):

A lot fo time the main way to help with this is to turn lambdas into real functions and type them. Then if needed, also type some variables. That gives concretes for the roc type checker to latch onto and propagate to catch the errors more locally.

view this post on Zulip Luke Boswell (Dec 04 2023 at 20:10):

I love the term pinning the types at that point, I heard it here somewhere

view this post on Zulip Brendan Hansknecht (Dec 04 2023 at 20:12):

Yeah, pinning is a great term for that. I wonder if we can add this to a guide somewhere. Just seams like a useful concept for many

view this post on Zulip Elias Mulhall (Dec 04 2023 at 20:57):

Pinning has a specific meaning in erlang/elixir, but this wouldn't be the first time a software word is used to mean two different things https://hexdocs.pm/elixir/1.16/pattern-matching.html#the-pin-operator

I guess the less obscure place pinning is used would be version pinning in some package managers.

view this post on Zulip LoipesMas (Dec 04 2023 at 21:24):

Rust also has its pinning: https://doc.rust-lang.org/std/pin/index.html ;]

view this post on Zulip Luke Boswell (Dec 04 2023 at 21:24):

@Richard Feldman would you be ok with a couple of sentences added to tutorial#type-annotations using this term? I think this is a really natural analogy for the interaction with the compiler being optional, and how you want to add annotations because it helps the compiler help you.

view this post on Zulip Brendan Hansknecht (Dec 04 2023 at 21:26):

When I think of pinning, I normally think of pinning memory for gpu related work. but I think the term is generic enough we can use it here too.


Last updated: Jul 06 2025 at 12:14 UTC