Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

cons doesn't always promote lists to HyObjects #568

Closed
hooblei opened this issue Apr 20, 2014 · 8 comments
Closed

cons doesn't always promote lists to HyObjects #568

hooblei opened this issue Apr 20, 2014 · 8 comments
Labels

Comments

@hooblei
Copy link
Contributor

hooblei commented Apr 20, 2014

=> (setv c (cons {"a" 1} []))
from hy.core.language import cons
c = cons({u'a': 1L, }, [])
=> (type (car c))
type(c[0L])
<class 'hy.models.dict.HyDict'>
=> (get (car c) "a")
c[0L][u'a']
Traceback (most recent call last):
  File "<input>", line 1, in <module>
  File "/home/maresp/workbench/cbf/venv/lib/python2.7/site-packages/hy/models/list.py", line 43, in __getitem__
    ret = super(HyList, self).__getitem__(item)
TypeError: list indices must be integers, not unicode
=>

The cons is because I'm not sure how to get/construct a HyDict otherwise

@tuturto
Copy link
Contributor

tuturto commented May 19, 2014

This looks peculiar and I'm not sure what to think of it.

=> (setv d {"a" 1})
=> (type d)
<class 'dict'>
=> (setv c (cons {"a" 1} []))
=> (type c)
<class 'hy.models.dict.HyDict'>

When assigning a dictionary directly, the type of it is "dict". When doing it via cons we end up with HyDict. Maybe something is leaking all the way back to the calling code. As far as I understand, HyDict should be used only internally by Hy and programs written with Hy should be using dict.

What kind of usage are you thinking of for this? What is the reason you would like to use HyDict instead of regular dictionaries?

@hooblei
Copy link
Contributor Author

hooblei commented May 24, 2014

What kind of usage are you thinking of for this? What is the reason you would like to use HyDict instead of regular dictionaries?

I have no need for a HyDict. I don't know about HyDict, but after reading your response, maybe the better bug would be: Hy casts dict into a HyDict when used in cons ... ?

@tuturto tuturto added the bug label May 24, 2014
@tuturto
Copy link
Contributor

tuturto commented May 24, 2014

That sounds like a bug to me.
Thanks for finding it out for us @hooblei
Minimum example for this (:key (first (cons {:key :value} nil))) gives the aforementioned error, when the expected output is :value

@olasd
Copy link
Member

olasd commented May 27, 2014

This is the behavior that I intended when I wrote cons cells.

The rationale behind it is that the HyCons is an internal, "quoted" Hy object (i.e. something that comes from the hy compiler world and not from the python world). It therefore made sense (at least in my mind) that the arguments to the cons function get "quoted" (i.e. turned into HyObjects). The intent was, for instance, to allow building dicts by consing stuff together, such as in (list* 1 2 3 4 {}) (which would build something equivalent to '{1 2 3 4})

I now notice that that behavior is broken too. When the cdr of the cons cell is an instance of a list, the HyObject cast doesn't happen which makes the behavior inconsistent.

If the whole wrapping behavior is deemed to be a bug, it can be fixed by dropping all the _wrap_values in hy/models/cons.py. If it's not, then the other bug should be fixed by wrapping the cdr before checking whether it is a list.

@olasd
Copy link
Member

olasd commented May 27, 2014

To further my point:

In common lisp, (1 2) is a two element list. (1 . 2) is a cons cell, or a two-element dotted list. Inputting both of those in the toplevel would evaluate them (i.e. try to call a function called 1 with the relevant argument). Calling (cons 1 2) would be equivalent to calling '(1 . 2), that is generating the quoted cons cell with car=1 and cdr=2. My intention was to replicate this behavior.

@agentultra
Copy link
Member

QUOTE merely returns its argument unevaluated.

`(1 . 2)

Is just a reader macro that expands to

(QUOTE (1 . 2))

Calling (cons 1 2) is calling a function called, CONS. It has completely different behaviour than QUOTE and is not equivalent.

On May 27, 2014, at 7:56 PM, Nicolas Dandrimont [email protected] wrote:

To further my point:

In common lisp, (1 2) is a two element list. (1 . 2) is a cons cell, or a two-element dotted list. Inputting both of those in the toplevel would evaluate them (i.e. try to call a function called 1). Calling (cons 1 2) would be equivalent to calling '(1 . 2), that is generating the quoted cons cell with car=1 and cdr=2. My intention was to replicate this behavior.


Reply to this email directly or view it on GitHub.

@Kodiologist Kodiologist changed the title TypeError in HyDict Item lookup cons doesn't always promote lists to HyObjects Mar 26, 2017
@gilch
Copy link
Member

gilch commented Jul 13, 2017

Did #1314 fix this one?

@Kodiologist
Copy link
Member

Honestly, your guess is as good as mine. Cons cells are a part of the language I've yet to touch.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

6 participants