Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Sorting nested list

4 views
Skip to first unread message

Gernot Pfanner

unread,
May 24, 2005, 5:26:39 AM5/24/05
to
Hi!

Please forgive me, if this is the 100.000th posting concerning sorting a
list. But at the moment I'm pretty confused, and so I ask you kindly for
your help...
Given something like
{{a,{2,4,1.,...}},{b,{3.2,-2,...}}}
How do I sort just the inner lists (i.e. e.g. {2,4,1.,...}), so that my
object finally looks like
{{a,{1.,2,4.,...}},{b,{-2,3.2,...}}}
In this spirit
With thanks in advance
Yours Gernot

Jens-Peer Kuska

unread,
May 25, 2005, 6:07:09 AM5/25/05
to
Hi,

{{a, {2, 4, 1., 8, 1, 4}}, {b, {3.2, -2, -6,
7, -7}}} /.
l_?(VectorQ[#, NumericQ] &) :> Sort[l]

??

Regards

Jens

"Gernot Pfanner" <pfan...@stud.uni-graz.at>
schrieb im Newsbeitrag
news:d6us0f$ivm$1...@smc.vnet.net...

Bob Hanlon

unread,
May 25, 2005, 6:12:29 AM5/25/05
to
expr= {{a,{2,4,1.}},
{b,{3.2,-2,1}}};

MapAt[Sort, #, 2]&/@expr

{{a, {1., 2, 4}},
{b, {-2, 1, 3.2}}}

expr/.x_?VectorQ:>Sort[x]

{{a, {1., 2, 4}},
{b, {-2, 1, 3.2}}}


Bob Hanlon

Jean-Marc Gulliet

unread,
May 25, 2005, 6:19:19 AM5/25/05
to
Hi Gernot,

I think the following method using Map and anonymous functions should do
the work:

In[1]:=
data={{b,{2,4,1.0}},{a,{3.2,-2,5,-3}}};

In[2]:=
Map[{#[[1]],Sort[#[[2]]]}&,data]

Out[2]=
{{b,{1.,2,4}},{a,{-3,-2,3.2,5}}}

Basically, the above expression tells Mathematica to go through the list
called "data" element by element, that is pair by pair in this case, and
to apply the anonymous function {#[[1]],Sort[#[[2]]]}& on each of them.
This function creates a new pair where the first element #[[1]] is not
changed and the second #[[2]] is sorted with the default option of the
command Sort.

Best regards,
/J.M.

János

unread,
May 25, 2005, 6:20:51 AM5/25/05
to

On May 24, 2005, at 5:12 AM, Gernot Pfanner wrote:

> Hi!
>
> Please forgive me, if this is the 100.000th posting concerning
> sorting a
> list. But at the moment I'm pretty confused, and so I ask you
> kindly for
> your help...
> Given something like
> {{a,{2,4,1.,...}},{b,{3.2,-2,...}}}
> How do I sort just the inner lists (i.e. e.g. {2,4,1.,...}), so
> that my
> object finally looks like
> {{a,{1.,2,4.,...}},{b,{-2,3.2,...}}}
> In this spirit
> With thanks in advance
> Yours Gernot
>

In[1]:=
lst = {{a, {2, 4, 1.}},
{b, {3.2, -2}}}
Out[1]=
{{a, {2, 4, 1.}},
{b, {3.2, -2}}}

In[16]:=
({#1[[1]], Sort[
#1[[2]]]} & ) /@ lst
Out[16]=


{{a, {1., 2, 4}},

{b, {-2, 3.2}}}

János

meznaric

unread,
May 25, 2005, 6:32:14 AM5/25/05
to
You should probably use pattern matching. For example for your list:

lst = {{a, {2, 4, 1}}, {b, {3.2, -2}}};
lst//. {a___, {b_, c_List /; ! OrderedQ[c, Less]}, d___} :> {a, {b,
Sort[c]}, d}

You can basically set up a transformation rule for any such structured
list.

Sebastjan

Tomas Garza Hernandez

unread,
May 25, 2005, 6:33:45 AM5/25/05
to
One possibility:

In[1]:=
ex={{a,Table[Random[Integer,{0,9}],{5}]},{b,

Table[Random[Integer,{0,9}],{5}]},{c,Table[Random[Integer,{0,9}],{5}]}}

Out[1]=
{{a,{5,3,3,6,0}},{b,{1,4,8,2,2}},{c,{0,0,6,5,5}}}

In[2]:=
Transpose[{#[[1]]&/@ex,Sort/@(#[[2]]&/@ex)}]

Out[2]=
{{a,{0,3,3,5,6}},{b,{1,2,2,4,8}},{c,{0,0,5,5,6}}}

Tomas Garza
Mexico City

Bill Rowe

unread,
May 25, 2005, 6:37:33 AM5/25/05
to
On 5/24/05 at 5:12 AM, pfan...@stud.uni-graz.at (Gernot Pfanner)
wrote:

>Please forgive me, if this is the 100.000th posting concerning
>sorting a list. But at the moment I'm pretty confused, and so I ask
>you kindly for your help... Given something like
>{{a,{2,4,1.,...}},{b,{3.2,-2,...}}} How do I sort just the inner
>lists (i.e. e.g. {2,4,1.,...}), so that my object finally looks
>like {{a,{1.,2,4.,...}},{b,{-2,3.2,...}}} In this spirit With
>thanks in advance Yours Gernot

I would do this as follows:

{First@#, Sort@Last@#}&/@list

where list contains the data you describe.
--
To reply via email subtract one hundred and four

dh

unread,
May 26, 2005, 4:33:15 AM5/26/05
to
Hi Gernot,
MapAt will apply a function exactly at the places you choose.E.g.:
d = {{a, {2, 4, 1.}}, {b, {3.2, -2, -3}}};
MapAt[Sort, d, Table[{i, 2}, {i, 1, Length[d]}]]
You may also use Map and take the arguments apart:
{First[#], Sort[Rest[#]]} & /@ d

Sincerely, Daniel

Wolf, Hartmut

unread,
May 26, 2005, 4:34:46 AM5/26/05
to

>-----Original Message-----
>From: Gernot Pfanner [mailto:pfan...@stud.uni-graz.at]
>Sent: Tuesday, May 24, 2005 11:13 AM
>Subject: Sorting nested list
>
>Hi!
>
>Please forgive me, if this is the 100.000th posting concerning
>sorting a
>list. But at the moment I'm pretty confused, and so I ask you
>kindly for
>your help...
>Given something like
>{{a,{2,4,1.,...}},{b,{3.2,-2,...}}}
>How do I sort just the inner lists (i.e. e.g. {2,4,1.,...}), so that my
>object finally looks like
>{{a,{1.,2,4.,...}},{b,{-2,3.2,...}}}
>In this spirit
>With thanks in advance
>Yours Gernot
>
>

Gernot,

in principle there are two complementary methods:

First, dissect your expression, apply Sort to the parts intended and
recompose.
Step by step, let

In[2]:=
l={{a,{2,4,1.,"..."}},{c,{3,1,2,"..."}},{b,{3.2,-2,"..."}}}


In[3]:= {keys, ll} = Transpose[l]
Out[3]=
{{a, c, b}, {{2, 4, 1., "..."}, {3, 1, 2, "..."}, {3.2, -2, "..."}}}


In[4]:= llsorted = Sort /@ ll
Out[4]=
{{1., 2, 4, "..."}, {1, 2, 3, "..."}, {-2, 3.2, "..."}}

In[5]:= Transpose[{keys, llsorted}]
Out[5]=
{{a, {1., 2, 4, "..."}}, {c, {1, 2, 3, "..."}}, {b, {-2, 3.2, "..."}}}


Put together into a one-liner, (e.g., there are lots of variants):

In[7]:= Transpose[{#1, Sort /@ #2}]& @@ Transpose[l]
Out[7]=
{{a, {1., 2, 4, "..."}}, {c, {1, 2, 3, "..."}}, {b, {-2, 3.2, "..."}}}

Second, keep your structure untouched but map Sort to the right parts:

In[10]:= MapAt[Sort, l, Thread[{Range[Length[l]],2}]]
Out[10]=
{{a, {1., 2, 4, "..."}}, {c, {1, 2, 3, "..."}}, {b, {-2, 3.2, "..."}}}


(Of course you may combine both methods appropriately.)


--
Hartmut Wolf

plizak

unread,
May 27, 2005, 5:07:30 AM5/27/05
to
I have a similar problem, I need to sort the same kind of list

{{a,{2,4,1.,...}}, {c, {1,2,...}},{b,{3.2,-2,.­..}}}

but I need to sort it based on the first element of each subarray,
while keeping the second element the same.

I did a pretty ugly solution (like 12 lines of code). Is there a
quicker more elegant way to sort this?

János

unread,
May 28, 2005, 5:37:00 AM5/28/05
to

In[9]:=
Sort[lst, #2[[2,1]] >=
#1[[2,1]] & ]
Out[9]=
{{c, {1, 2}},


{a, {2, 4, 1.}},
{b, {3.2, -2}}}

János

meznaric

unread,
May 28, 2005, 5:38:31 AM5/28/05
to
Plizak: Simply apply Sort:
Sort[{{a,{2,4,1}}, {c, {1,2}},{b,{3.2,-2}}}]

will give you the sorted list you are looking for:
{{a, {2, 4, 1}}, {b, {3.2, -2}}, {c, {1, 2}}}

Sebastjan

Bill Rowe

unread,
May 28, 2005, 5:53:01 AM5/28/05
to
On 5/27/05 at 4:56 AM, pli...@gmail.com (plizak) wrote:

>I have a similar problem, I need to sort the same kind of list

>{{a,{2,4,1.,...}}, {c, {1,2,...}},{b,{3.2,-2,.≠..}}}

>but I need to sort it based on the first element of each subarray,
>while keeping the second element the same.

>I did a pretty ugly solution (like 12 lines of code). Is there a
>quicker more elegant way to sort this?

Is this what you want?

In[8]:=
data = {{a, {2, 4, 1.}}, {c, {1, 2}}, {b, {3.2, -2}}};
Sort[data, OrderedQ[{#1[[2,1]], #2[[2,1]]}] & ]

Out[9]=
{{c, {1, 2}}, {a, {2, 4, 1.}}, {b, {3.2, -2}}}

Carl K. Woll

unread,
May 29, 2005, 1:12:16 AM5/29/05
to
"plizak" <pli...@gmail.com> wrote in message
news:d76o0i$7mu$1...@smc.vnet.net...

The simplest idea is to use Sort with an ordering function. An alternate
idea, which is in general much quicker, is to generate a key for each
element in the array, and then use Ordering on this list of keys. In your
case, we would do the following:

In[12]:=


data = {{a, {2, 4, 1.}}, {c, {1, 2}}, {b, {3.2, -2}}};

keys = data[[All, 2, 1]]
Out[13]=
{2, 1, 3.2}

Then, use Ordering to get the sorted list:

In[14]:=
data[[Ordering[keys]]]
Out[14]=


{{c, {1, 2}}, {a, {2, 4, 1.}}, {b, {3.2, -2}}}

Let's compare the timing for this approach versus using Sort with an
ordering function:

data = Table[{Random[], Table[Random[], {10}]}, {10^5}];

In[16]:=
r1 = data[[Ordering[data[[All, 2, 1]]]]]; // Timing
r2 = Sort[data, #2[[2, 1]] > #1[[2, 1]] &]; // Timing
r1 === r2
Out[16]=
{0.157 Second, Null}
Out[17]=
{6.343 Second, Null}
Out[18]=
True

We see that the Ordering approach is about 40 times faster for this data
set.

Carl Woll


0 new messages