This is a very beginner question. I would like to check if a key exists in a dictionary.
julia> 1 in Dict(1=>'a', 2=>'b')
ERROR: AbstractDict collections only contain Pairs;
Either look for e.g. A=>B instead, or use the `keys` or `values`
function if you are looking for a key or value respectively.
Stacktrace:
[1] error(::String) at ./error.jl:33
[2] in(::Int64, ::Dict{Int64,Char}) at ./abstractdict.jl:28
[3] top-level scope at REPL[9]:1
This makes sense, a dictionary contains Pairs and not keys.
I can do this:
julia> 1 in keys(Dict(1=>'a', 2=>'b'))
true
But I think keys() returns an iterator, and the in operator iterates over all keys until it finds the key. AFAIK iterators only support sequential iteration. Using a linear search to find a key in a hashmap is crazy.
I thought @StefanKarpinski comment was interesting⌠and it looks like the âinâ form is faster than haskeyâŚ
Please tell me what I did wrong in this microbenchmark
edit: and i found my mistake almost as soon as i posted⌠new code.
function f1(d, l)
x = true
for i=1:length(l)
x = x && haskey(d, l[i])
end
x
end
function f2(d, l)
x = true
for i=1:length(l)
x = x && l[i] in keys(d)
end
x
end
function main()
n = 500000
d = Dict{Int, Char}()
for i=1:n
d[rand(1:n)] = Char(rand(Int('a'):Int('z')))
end
# be sure and include some look-ups that will fail.
l = rand(1:n+1000, n)
@time f1(d, l)
@time f2(d, l)
end
That is very good to know. Iâm a newcomer to Julia and multi dispatch, and I donât know how to look for documentation. In a single-dispatch OOP language, I could simply look up the method of a class (and the class would already be given). But with Julia, I find it hard to find documentation for things. For example, the keys function has this documentation ( Collections and Data Structures ¡ The Julia Language )
For an iterator or collection that has keys and values (e.g. arrays and dictionaries), return an iterator over the keys.
It does not (and probably cannot?) tell what kind of iterator is returned, because it depends on the various methods, and they can be added by external packages. I can only be sure about one thing: it returns an iterator. I already read most the manual and I can recall that iteration was described at âInterfacesâ ( Interfaces ¡ The Julia Language ) but it also does not define what an iterator is. Of course, there are examples showing iterations over various data types, but that is not a definition.
I can also see that there are multiple methods (by looking at methods(keys)) but that doesnât help either, because it is just a list of line numbers in the source code, and they donât have method-specific documentation (or at least I donât know where).
How am I supposed to know, that the iterator of a Dict is a KeysIterator and that it can be efficiently tested for key containment? What is a KeysIterator anyway? I just tried to search for it in the official docs, but nothing was found.
After all, I remain uncertain and I have to ask lots of questions here. Iâm constantly asking for help and that is uncomfortable. Am I using the documentation the wrong way? Is there a better way to use it?
Ultimately, it almost doesnât matter that iterating over keys gives you a KeysIterator. Highly unlikely that type should actually appear in your code, even if your code makes use of it. The keys functions returns an iterator, iterators in Julia adhere to a common interface, and things âJust Workâ if you donât overtype your code.
I agree with your comments here that sometimes the documentation is sparse. Itâs a rapidly evolving project where the main Julia folks are often busy with more âseriousâ work like threading support and compiler worker. I suggest that if you have learned something from this discourse thread, that you may submit a PR to the documentation in the relevant section.
Offtopic: I remember that a long time ago MSDN used to have a âcomments/snippetsâ section at the end of their doc pages where folks would submit snippets of code on the particular topic. I think something like that for Julia would be great. Maybe not particularly relevant to haskey or Dicts but can be extremely useful for packages like Query.
The part in the manual about the iterator interface is the definition of an iterator â anything that implements that interface is an iterator.
You donât actually need to know that to use keys(dict). The point is to abstract away these implementation details. ?keys documents the actual usage â it even has a sentence about Dict.
To be fair, the documentation can always be improved. But it is frequently useful to look at the âverbsâ (functions) like keys in addition to the ânounsâ (types).
It is not easy to adjust from an OOP language to multimethods, especially if you are very experienced with OOP. Just give it time.