On Jun 3, 2009, at 12:53 PM, CuppoJava wrote:
Is there a function that will return true iff calling seq on it's argument will not throw an error? I thought it was seq?, but (seq? [1 2 3]) returns false.
Such a function might be called "seqable?". As far as I know it doesn't exist currently. I've wanted it in the past as well.
The "seq" function is implemented in Java as RT.seq: static public ISeq seq(Object coll){ if(coll instanceof ASeq) return (ASeq) coll; else if(coll instanceof LazySeq) return ((LazySeq) coll).seq(); else return seqFrom(coll); } which calls RT.seqFrom: static ISeq seqFrom(Object coll){ if(coll instanceof Seqable) return ((Seqable) coll).seq(); else if(coll == null) return null; else if(coll instanceof Iterable) return IteratorSeq.create(((Iterable) coll).iterator()); else if(coll.getClass().isArray()) return ArraySeq.createFromObject(coll); else if(coll instanceof String) return StringSeq.create((String) coll); else if(coll instanceof Map) return seq(((Map) coll).entrySet()); else { Class c = coll.getClass(); Class sc = c.getSuperclass();throw new IllegalArgumentException("Don't know how to create ISeq from: " + c.getSimpleName());
} } From that we could derive isSeqable in Java as static public bool isSeqable(Object coll){ return (coll instanceof ISeq) || (coll instanceof Seqable) || (coll == null) || (coll instanceof Iterable) || (coll.getClass().isArray()) || (coll instanceof String) || (coll instanceof Map); }(ASeq and LazySeq both implement ISeq so their two tests can be collapsed into one.)
I've checked in a Clojure version to clojure.contrib.core: user=> (doc seqable?) ------------------------- clojure.contrib.core/seqable? ([x]) Returns true if (seq x) will succeed, false otherwise. nil user=>The one critique I have of this is that one might expect (seqable? x) to return true only if (instance? clojure.lang.Seqable x) returns true. I think the name seqable? is ideal otherwise though, so I used it.
--Steve
smime.p7s
Description: S/MIME cryptographic signature