Discover MakerZone

MATLAB and Simulink resources for Arduino, LEGO, and Raspberry Pi

Learn more

Discover what MATLAB® can do for your career.

Opportunities for recent engineering grads.

Apply Today

Thread Subject:
Finding rows preserving order

Subject: Finding rows preserving order

From: HJ

Date: 20 Mar, 2014 04:56:05

Message: 1 of 8

I have an Nx2 matrix, allCoords, and an Mx2 matrix, desiredCoords, where M<N. I need to extract the indices of all the rows in allCoords that are in desiredCoords, in the same order as they appear in desiredCoordinates. As a simple example:

allCoords =
     8 14
     8 13
     8 12
    17 5
    17 6
    17 7

desiredCoords =
    17 6
     8 13
     8 12

In this case, find(ismember(allCoords,desiredCoords,'rows')) gives me [2 3 5], but I need to find an expression that returns [5 2 3], in other words, one that preserves the ordering in allCoords.

I sense that this should be a very simple one-liner, and I've tried the various output forms of ismember and find, but so far no luck. Can anyone refresh my addled brain on how to do this?

Thanks,

-H

Subject: Finding rows preserving order

From: HJ

Date: 20 Mar, 2014 05:11:08

Message: 2 of 8

Ack. I managed not one but two typos in the above post. The line

> the same order as they appear in desiredCoordinates

should read "the same order as they appear in desiredCoords", and, more importantly,

> one that preserves the ordering in allCoords.

should read "one that preserves the ordering in ***desiredCoords***" (emphasis added).

Serves me right for posting so late at night. Sorry for any confusion, and thanks in advance for any pointers.

-H

Subject: Finding rows preserving order

From: dpb

Date: 20 Mar, 2014 12:40:02

Message: 3 of 8

On 3/20/2014 12:11 AM, HJ wrote:
> Ack. I managed not one but two typos in the above post. The line
>
>> the same order as they appear in desiredCoordinates
>
> should read "the same order as they appear in desiredCoords", and, more
> importantly,
>
>> one that preserves the ordering in allCoords.
>
> should read "one that preserves the ordering in ***desiredCoords***"
> (emphasis added).
...

Using the alternate returns of locations found and retrieving with that
indexing vector instead of the primary default returned sorted vector
should solve the problem.

--

Subject: Finding rows preserving order

From: HJ

Date: 20 Mar, 2014 16:10:22

Message: 4 of 8

dpb <none@non.net> wrote in message <lgenj1$d5m$1@speranza.aioe.org>...
> Using the alternate returns of locations found and retrieving with that
> indexing vector instead of the primary default returned sorted vector
> should solve the problem.

Hi dpb,

Thanks for the response. Sorry if I'm being obtuse, but I don't quite understand what you have in mind. I already tried

[ii,jj,vv] = find(ismember(allCoords,desiredCoords,'rows'))

which gives

ii = [2 3 5]' and jj = vv = [1 1 1]'

Is that not what you meant by using the indexing vector(s)?

TIA,

-H

Subject: Finding rows preserving order

From: dpb

Date: 20 Mar, 2014 16:33:50

Message: 5 of 8

On 3/20/2014 11:10 AM, HJ wrote:
> dpb <none@non.net> wrote in message <lgenj1$d5m$1@speranza.aioe.org>...
>> Using the alternate returns of locations found and retrieving with
>> that indexing vector instead of the primary default returned sorted
>> vector should solve the problem.
>
> Hi dpb,
>
> Thanks for the response. Sorry if I'm being obtuse, but I don't quite
> understand what you have in mind. I already tried
>
> [ii,jj,vv] = find(ismember(allCoords,desiredCoords,'rows'))
>
> which gives
>
> ii = [2 3 5]' and jj = vv = [1 1 1]'
>
> Is that not what you meant by using the indexing vector(s)?

Sorry, what I was _thinking_ despite what I wrote is intersect() not
ismember()

 >> [~,~,ia]=intersect(d,a,'rows','stable')
ia =
      5
      2
      3
 >>

This works if there are no repeats; unfortunately, no builtin Matlab
function returns the full set in that case but only the minimum.

If that's the case you'll have to build an arrayfun() or accumarray()
expression.

--

Subject: Finding rows preserving order

From: HJ

Date: 20 Mar, 2014 17:22:08

Message: 6 of 8

dpb <none@non.net> wrote in message <lgf59f$mqb$1@speranza.aioe.org>...
> Sorry, what I was _thinking_ despite what I wrote is intersect() not ismember()

No worries, and thanks for the clarification. Glad I wasn't just being dense.
> >> [~,~,ia]=intersect(d,a,'rows','stable')
> ia =
> 5
> 2
> 3

Ugh. I'm forced to work with R2006b on this project (long story), and the version of INTERSECT here doesn't take the fourth argument (which, now that I've looked at the docs, does exactly what I need). Sigh.

FWIW, I did come up with this workaround:

>> [tf,loc]=(ismember(allCoords,desiredCoords,'rows'));
>> dummy=sortrows([loc(find(loc)) find(loc)],1); dummy=dummy(:,2)
dummy =
     5
     2
     3

... which feels like an ugly hack, but at least it's vectorized. I may end up just using a FOR loop -- since the second line does a sort, I'll need to try TIC/TOC to see if there's any significant speed difference (obviously my actual arrays are much larger than the example I started with).

If you have any ideas/riffs on the above, I'd love to hear them. Thanks again for your suggestion regarding INTERSECT.

-H

Subject: Finding rows preserving order

From: dpb

Date: 20 Mar, 2014 17:37:59

Message: 7 of 8

On 3/20/2014 12:22 PM, HJ wrote:
> dpb <none@non.net> wrote in message <lgf59f$mqb$1@speranza.aioe.org>...
>> Sorry, what I was _thinking_ despite what I wrote is intersect() not
>> ismember()
>
...

> Ugh. I'm forced to work with R2006b on this project (long story), and
> the version of INTERSECT here doesn't take the fourth argument (which,
> now that I've looked at the docs, does exactly what I need). Sigh.
>
> FWIW, I did come up with this workaround:
>
>>> [tf,loc]=(ismember(allCoords,desiredCoords,'rows'));
>>> dummy=sortrows([loc(find(loc)) find(loc)],1); dummy=dummy(:,2)
> dummy =
> 5
> 2
> 3
>
> ... which feels like an ugly hack, but at least it's vectorized. I may
> end up just using a FOR loop -- since the second line does a sort, I'll
> need to try TIC/TOC to see if there's any significant speed difference
> (obviously my actual arrays are much larger than the example I started
> with).
>
> If you have any ideas/riffs on the above, I'd love to hear them. Thanks
> again for your suggestion regarding INTERSECT.

That's basically what the TMW intersect() does. Only
question/suggestion would be whether you have SORTROWS in that release
or not.

It's quite possible a straightforward loop might win; INTERSECT is just
an m-file, too.

--

Subject: Finding rows preserving order

From: Bruno Luong

Date: 20 Mar, 2014 23:06:25

Message: 8 of 8

"HJ" <hjfarkmail.notthispart@notthisparteither.lycos.com> wrote in message <lgdsd5$hb6$1@newscl01ah.mathworks.com>...
> I have an Nx2 matrix, allCoords, and an Mx2 matrix, desiredCoords, where M<N. I need to extract the indices of all the rows in allCoords that are in desiredCoords, in the same order as they appear in desiredCoordinates. As a simple example:
>
> allCoords =
> 8 14
> 8 13
> 8 12
> 17 5
> 17 6
> 17 7
>
> desiredCoords =
> 17 6
> 8 13
> 8 12
>
> In this case, find(ismember(allCoords,desiredCoords,'rows')) gives me [2 3 5], but I need to find an expression that returns [5 2 3], in other words, one that preserves the ordering in allCoords.
>

% Try this

>> [~,LOCB] = ismember(desiredCoords,allCoords,'rows')

LOCB =

     5
     2
     3

% Bruno

> -H

Tags for this Thread

What are tags?

A tag is like a keyword or category label associated with each thread. Tags make it easier for you to find threads of interest.

Anyone can tag a thread. Tags are public and visible to everyone.

Contact us