Take the 2-minute tour ×
Mathematica Stack Exchange is a question and answer site for users of Mathematica. It's 100% free, no registration required.

Consider the function f which should behave as

f[{{1, 2}, {3, 4}, {5, 6, 7}}]
{f[{1, 2}], f[{3, 4}], f[{5, 6, 7}]}

The following code doesn't worked as expectation

fromDig[ls_?VectorQ] := 10^Range[Length@ls - 1, 0, -1].ls;
SetAttributes[fromDig, Listable];
fromDig@{{1, 2}, {3, 4}, {5, 6}}

I figured out a way, using Compile,

Clear["Global`*"];
cfromDig = Compile[{{A, _Integer, 1}},
 10^Range[Length@A - 1, 0, -1].A, RuntimeAttributes -> {Listable}];
cfromDig[{{1, 2}, {3, 4}, {5, 6}}]

Is there a better way?

share|improve this question
    
I think this is a duplicate. Let me look. -- There are so many posts that mention Listable or threading that I am finding it difficult. –  Mr.Wizard Sep 26 '13 at 5:45
    
I am not sure if I understand, but why not just: fromDig2[ls_List] := 10^Range[Length@# - 1, 0, -1].# & /@ ls; fromDig2@{{1, 2}, {3, 4}, {5, 6}}? (or FromDigits /@ {{1, 2}, {3, 4}, {5, 6}}:) ) –  Pinguin Dirk Sep 26 '13 at 5:59
    
...or fromDig3[ls__] := 10^Range[Length@{ls} - 1, 0, -1].{ls}; fromDig3 @@@ {{1, 2}, {3, 4}, {5, 6}} –  gpap Sep 27 '13 at 10:47

1 Answer 1

up vote 10 down vote accepted

I'm pretty sure this is a duplicate but I spent 15 minutes looking for it and couldn't find it, so I'm just going to answer for now.

Instead of using Listable you can manually map over non-vector lists:

f[v_?VectorQ] := oper[v]
f[ls_List] := f /@ ls;

f[{{1, 2}, {3, 4}, {5, 6, 7}}]
{oper[{1, 2}], oper[{3, 4}], oper[{5, 6, 7}]}

Extension

In an attempt to make this answer more unique, consider the advanced behavior of Listable functions wherein non-list arguments are distributed:

SetAttributes[ff, Listable]
ff["x", {1, 2, 3}, {4, 5, 6}]
{ff["x", 1, 4], ff["x", 2, 5], ff["x", 3, 6]}

We may wish to have this behavior extended, in a fashion at least, to our "vector atoms" as used above. The simplest method I can think of is to use Thread, which has the same behavior is Listable though only at level one, and guard the vectors form recognition and threading. Here an unoptimized first pass at implementation:

g[a___] /; MemberQ[{a}, x_List /; ! VectorQ[x]] :=
  Module[{h},
    g @@@ Replace[Thread@Replace[Hold[a], v_?VectorQ :> h[v], {1}], h@x_ :> x, {2}]
  ]

Now:

g[1, {2, 3}, {{{4}}, {5, 6}, 7}]
{{g[1, {2, 3}, {4}]}, g[1, {2, 3}, {5, 6}], g[1, {2, 3}, 7]}

Note that the vector {2, 3} is distributed as 1 is, while the nested lists are threaded. When {4} is encountered it is also treated as atomic, but its surrounding List is transferred to the output: {g[1, {2, 3}, {4}]}.

share|improve this answer
3  
I have the search problem for long time, too :)) Do you think we should move meta.mathematica.stackexchange.com/questions/1086/… question to the main site... –  s.s.o Sep 26 '13 at 8:34
    
@s.s.o It's migrated now. I hope you get an answer at last. –  Mr.Wizard Sep 26 '13 at 12:03

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.