stuck on a type problem

26 views
Skip to first unread message

Nate Griswold

unread,
Jul 25, 2020, 1:52:43 PM7/25/20
to Racket Users
Hello. I am stuck on a probably simple type problem and was wondering if someone could help:

I'll just give the actual functions im using:

```
(struct Character ([bytes16 : Bytes]))
(define substr (make-bytes 128))
(: make-character (-> Integer Integer Character))
(define (make-character s e)
  (Character (subbytes substr (* 2 s) (* 2 e))))
```

What i want is a function like:

```
(: blah (-> (List Integer Integer) Character))
(define blah (λ (rng) (apply make-character rng)))
```

Which works.

But note i can't just type (λ (rng) (apply make-character rng)) into the REPL, because i get:

; readline-input:5:14: Type Checker: Bad arguments to function in `apply':
; Domain: Integer Integer
; Arguments:  Any
;   in: (apply make-character rng)

I think because i need the explicit (List Integer Integer) annotation to unify with (Listof Integer)

Anyway, i wanted to make my code simpler so i was wondering if i could curry and partially apply. So i was digging around in the reference and tried:

```
(: blah2 (-> (List Integer Integer) Character))
(define2 blah2 ((curry (inst apply Integer Character)) make-character)
```

But i get:

; readline-input:8:40: Type Checker: type mismatch
;   expected: (-> Integer * Character)
;   given: (-> Integer Integer Character)
;   in: make-character

Looking at the typed racket reference and the type of apply, thought the star meant i could have many integers. Actually to be honest the discussion in typed racket reference "1.6 - Other Type Constructors" left me hanging a little bit on the function types, I am a pretty green on working with racket types and types in general. I thought this would unify but i guess i am completely wrong. Does anyone know what i am doing wrong exactly or what a very abbreviated form for what i want (behavior of blah) is?

Sorry if this is basic i am a little lost on it as you can probably tell.

Thank you

Nate


A Mauer-Oats

unread,
Jul 25, 2020, 2:47:12 PM7/25/20
to Racket Users
Problem 1:


> But note i can't just type (λ (rng) (apply make-character rng)) into the REPL,

If you're using Typed Racket, you probably want type signatures in your lambdas as well.
In this case, you need to specify the type of `rng` (at least):

```
(λ ([rng : (List Integer Integer)]) (apply make-character rng))
```

Problem 2:

; readline-input:8:40: Type Checker: type mismatch
;   expected: (-> Integer * Character)
;   given: (-> Integer Integer Character)
;   in: make-character

I'm not sure about this one; it looks like you are currying _apply_... Don't you just want `(curry make-character)`?
Like:

```
(define blahh ((curry make-character) 10))
```

Problem 2b: understanding the complaint.
The type checker is complaining that it wants something that takes in an arbitrary number of integers (0 or more), but you have given it something that takes in exactly two integers. Your inputs need to be a superset of the allowable inputs, not a subset.


; readline-input:8:40: Type Checker: type mismatch
;   expected: (-> Integer * Character)
;   given: (-> Integer Integer Character)
;   in: make-character



Possibly helpful:

> the discussion in typed racket reference "1.6 - Other Type Constructors" left me hanging a little bit on the function types

If you haven't read the Typed Racket Guide, section 4.2 and maybe 4.3 should be easier going than the reference.

Nate Griswold

unread,
Jul 25, 2020, 5:00:11 PM7/25/20
to A Mauer-Oats, Racket Users
Thank you for the detailed reply! Please see below...

On Sat, Jul 25, 2020 at 1:47 PM A Mauer-Oats <maue...@gmail.com> wrote:
Problem 1:

> But note i can't just type (λ (rng) (apply make-character rng)) into the REPL,

If you're using Typed Racket, you probably want type signatures in your lambdas as well.
In this case, you need to specify the type of `rng` (at least):

```
(λ ([rng : (List Integer Integer)]) (apply make-character rng))
```

Thanks this makes sense.


Problem 2:

; readline-input:8:40: Type Checker: type mismatch
;   expected: (-> Integer * Character)
;   given: (-> Integer Integer Character)
;   in: make-character

I'm not sure about this one; it looks like you are currying _apply_... Don't you just want `(curry make-character)`?
Like:

```
(define blahh ((curry make-character) 10))
```


Actually, what i want is the behavior of the original blah function but written simpler. So it's something that takes 2 ints and produces a `Character` from the byte stream held by blah.

Problem 2b: understanding the complaint.
The type checker is complaining that it wants something that takes in an arbitrary number of integers (0 or more), but you have given it something that takes in exactly two integers. Your inputs need to be a superset of the allowable inputs, not a subset.

; readline-input:8:40: Type Checker: type mismatch
;   expected: (-> Integer * Character)
;   given: (-> Integer Integer Character)
;   in: make-character


Well, ok. Hm. If i guess if i write this function
```
(: apply2 (All (a b) (-> (-> a a b) (List a a) b)))
(define (apply2 f arglist) (apply f arglist))
```

Then i can do what i was trying to do with:

```
(: f (-> (List Integer Integer) Character))
(define f ((curry (inst apply2 Integer Character)) make-character))
```

Which is definitely not that simple, so i still am left wondering if i can simplify this all by putting the type system to work somehow... I was thinking if the original function "blah" function could bend apply to its will then i should be able to do something similar in a little different way.

Nate



Possibly helpful:

> the discussion in typed racket reference "1.6 - Other Type Constructors" left me hanging a little bit on the function types

If you haven't read the Typed Racket Guide, section 4.2 and maybe 4.3 should be easier going than the reference.


This is ok, but there doesn't seem to be any discussion in the guide of the different function types with stars or ellipses that I have found.

--
You received this message because you are subscribed to the Google Groups "Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to racket-users...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/racket-users/083c3f2f-dfbd-4957-8b3d-690cab6d674eo%40googlegroups.com.
Reply all
Reply to author
Forward
0 new messages