-
-
Notifications
You must be signed in to change notification settings - Fork 398
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
keys(::JuMPDict) returns an iterator containing tuples #646
Comments
Well, there has to be an inconsistency somewhere because if a JuMPDict is indexed over multiple dimensions then the only thing that makes sense to return is a tuple. You can get the code working by writing:
|
Hmm... yeah I see what you mean. It still seems a little weird that they objects you get when iterating over keys() are not actually valid keys. Would it make sense to add the following additional version of getindex:
? (This has the side effect of making |
I think that would break the case when the index set is a set of tuples. The internal key would be |
Would it work if the index set only contains tuples? i.e. would it break only if the index set contains both tuple and non tuple items? (I didn't dig deep enough to answer this question myself.) If that is the case, are there even any foreseeable cases when the index set would contain both tuples and non-tuples? I don't see a great way to fix this without changing the internal representation, and I don't have any good alternative internal representations to suggest. Feel free to close this issue if you don't plan on fixing it. |
It's foreseeable that if we break this, someone will complain :). We're open to further discussion and PRs, but progress here likely won't come from me since it's pretty confusing for me to wrap my head around all of the corner cases. |
Maybe the solution here is to use something like |
@zsunberg I think the case we would need to worry about is something like I = Any[2,(2,)]
@variable(m, x[I]) |
@IssamT, what do you think about the |
@mlubin I don't think it makes it better since the behavior of keys that was mentioned by @zsunberg isn't something only related to Julia, but you find it also in Java C++ Python ... keeping the same behavior is nice even when moving from a language to another, so making keys have different meaning in two subsets of Julia isn't good in my opinion. However there have always been some kind of language abuse when writing mathematical modeling languages because mathematicians want them simple :) however it is the first time I see keys used to mean "indices" of an "array" (storing a dictionary) |
@mlubin maybe because multidimensional arrays are less common, I would find it less weird if I had to write
It even make sense because if you give me a single tuple containing the indices I need to access an element in a multidimensional array, I know intuitively that I need to elapse the tuple and provide its content to the operator [] of the multidimensional array This may solve the problem with JuMPArray but not with JuMPDict... However as I am new to JuMP I haven't yet used JuMPDict . is it exposed to users? or only an internal type? |
See also Julia's |
+1 for eachindex as long as you call the container JuMPArray |
Well, how are people supposed to write generic code that works for both JuMPArray and JuMPDict then? Users shouldn't care about what internal data structure we use for the collection. |
I digged more into the code and I understood that JuMPArray and JuMPDict are usefull in different situations . I understand there is the need for both with generic functions. And I agree that eachindex isn't a good idea. I have another suggestion: When using classic arrays, this code
returns 6 as expected Notice that we write A[ci] and not A[ci...] and there is no possible ambiguity because ci is of type CartesianIndex{N} and not a tuple. So instead of defining JuMP.keys that have different behavior than normal keys, how about giving a new name to the actual new thing JuMP.CartesianIndex{T,N}. We need to add T because our indices are not necessarily integers and hence it would be even better to call it JuMP.CartesianKey{T,N} And combine this with the solution suggested by @zsunberg |
Yes, having a wrapper type like that could be a good idea. |
@IssamT, we're open for pull requests if you'd like to sketch out a solution |
@mlubin, I have looked at the code (both the one around JuMP iterators as well as the one around Base CartesianIndex). But to be honest, there are still many Julia features that I don't master yet since I am new to Julia. However, if this issue persists for a couple of months, I would probably get back to it... |
Another issue to consider when redesigning JuMPContainers is whether it is interesting or not to allow iterators ( This code works as expected
But neither of these for loops work since the type of
If we change
|
@IssamT, we already collect iterators internally in some situations. I don't think we should disallow indexing with iterators, but if needed JuMP should call |
@mlubin I looked more into the issue I cited in my previous comment and the problem is not limited to iterators. The documentation states that
But if the sets are not ordered, indexable collections Hence you also can't use an index set of type Of course when you add In this "generated" function, that I don't understand well, is there a way to return the next element without using
|
Replace JuMPDict with Dict. Rewrite JuMPArray to be compatible with AbstractArray. Explicit keyword argument in macro to force container type. Closes #1099 Closes #1047 Closes #417 (collect is now well defined for Array, JuMPArray, and Dict) Closes #833 (`eachindex` and `indices` are defined for JuMPArray) Closes #740 (dot broadcast syntax is now the default, no need to explicitly define vectorized functions) Closes #922 (fixed by checking for duplicates) Closes #933 (corollary: closes #346) Closes #643 (colons work for Array and JuMPArray, obviously not Dict) Closes #730 (end is not supported for JuMPArray) Closes #646 (we now rely on built-in iteration behavior for Dict)
Replace JuMPDict with Dict. Rewrite JuMPArray to be compatible with AbstractArray. Explicit keyword argument in macro to force container type. Closes #1099 Closes #1047 Closes #417 (collect is now well defined for Array, JuMPArray, and Dict) Closes #833 (`eachindex` and `indices` are defined for JuMPArray) Closes #740 (dot broadcast syntax is now the default, no need to explicitly define vectorized functions) Closes #922 (fixed by checking for duplicates) Closes #933 (corollary: closes #346) Closes #643 (colons work for Array and JuMPArray, obviously not Dict) Closes #730 (end is not supported for JuMPArray) Closes #646 (we now rely on built-in iteration behavior for Dict)
Is it the correct behavior for
keys(::JuMPDict)
to return aKeyIterator
for a dictionary with tuples as keys? This seems strange when the keys for theJumpDict
are not tuples.In particular, if I have a variable
u
and aJumpDict
from solving another problem stored ininitial.u
, I can't do the followingThe text was updated successfully, but these errors were encountered: