James, I was surprised myself that I knew the answer. I had a guess as to 
the origin of this information so I Googled to confirm. The problem was 
mentioned in one of the Java Puzzlers [1] talks [2] by Joshua Bloch and Bob 
Lee. The same issue was also discussed on Stack Overflow [3] (which I 
discovered in the process of the aforementioned Googling).

[1] http://www.javapuzzlers.com/
[2] 
http://strangeloop2010.com/system/talks/presentations/000/014/450/BlochLee-JavaPuzzlers.pdf?1290462274
 
- See puzzle #5
[3] 
http://stackoverflow.com/questions/8630279/why-cant-i-hold-enummap-entries-via-a-for-loop-even-if-i-use-final-best-w

Thanks,
Elias.

On Thursday, October 3, 2013 5:29:24 AM UTC-4, James Warren wrote:
>
> Thank you for your responses, Marek and Elias.
>
> Elias, you hit it square on the head - I was using Java 6, and changing to 
> Java 7 corrected the issue. If you don't mind me asking, how did you even 
> know about this behavior? This isn't the type of information you typically 
> see on Hacker News, albeit much more helpful! :)
>
> On Wednesday, October 2, 2013 7:17:40 PM UTC-7, Elias Zaretsky wrote:
>>
>> Are you using Java 6 by any chance? This issue may be due to a gotcha in 
>> java.util.EnumMap. The implementation of the entry set iterator in EnumMap 
>> in Java 6 is unorthodox [1]. Its next() method always returns the same 
>> object, which is mutated to "point" to different entries in the map as the 
>> iterator moves forward. This explains the behavior you are observing. Try 
>> switching to Java 7 or make sure you call the keys function every time you 
>> need the sequence of keys.
>>
>> [1] 
>> http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/6-b14/java/util/EnumMap.java#EnumMap.EntryIterator
>>
>> Thanks,
>> Elias.
>>
>> On Wednesday, October 2, 2013 5:19:31 PM UTC-4, James Warren wrote:
>>>
>>> I've been using Clojure for a couple months, so while I feel comfortable 
>>> with it, I'm not certain whether some unusual behavior I encountered is a 
>>> bug or a lack of understanding on my part.  (I suspect the latter.)
>>>
>>> The context arose from using Clojure reflection to inspect a class 
>>> generated by Apache Thrift <http://thrift.apache.org>. Such classes 
>>> have a static, unmodifiable map describing the members of the class. I 
>>> wrote a function to extract the keys of this map; it initially appears to 
>>> work, but "def"ing the results to a symbol and repeatedly using that symbol 
>>> returns inconsistent results.
>>>
>>> I've boiled it down to a smaller example that replicates the result: (gist 
>>> available <https://gist.github.com/jameswarren/6799309>)
>>>
>>> // Java class
>>>
>>> public class DummyClass {
>>>     public enum DummyEnum {
>>>     FIRST, SECOND, THIRD
>>>   }
>>>  
>>>   public static final Map<DummyEnum, String> dummyMap;
>>>   static {
>>>     Map<DummyEnum, String> tmpMap = new EnumMap<DummyEnum, 
>>> String>(DummyEnum.class);
>>>     tmpMap.put(DummyEnum.FIRST, "first");
>>>     tmpMap.put(DummyEnum.SECOND, "second");
>>>     tmpMap.put(DummyEnum.THIRD, "third");    
>>>     dummyMap = Collections.unmodifiableMap(tmpMap);
>>>   }
>>> }
>>>
>>> // Clojure ns
>>>
>>> (ns refbug.core
>>>   (:import [refbug DummyClass]))
>>>  
>>> (defn foo [^Class c]
>>> ;; note: (into [] (keys (clojure.lang.Reflector/getStaticField c 
>>> "dummyMap")))) works
>>>   (keys (clojure.lang.Reflector/getStaticField c "dummyMap")))
>>>  
>>> (def m (foo DummyClass))
>>> (println m)
>>> ;; (#<DummyEnum FIRST> #<DummyEnum SECOND> #<DummyEnum THIRD>)
>>> (println m)
>>> ;; (#<DummyEnum THIRD> #<DummyEnum THIRD> #<DummyEnum THIRD>)
>>>
>>> Two different values upon successive calls using m.  Is this expected?  And 
>>> if so, why?
>>>
>>> Many thanks,
>>> -James
>>>
>>>

-- 
-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Reply via email to