cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 
Try the Materials Informatics Toolkit, which is designed to easily handle SMILES data. This and other helpful add-ins are available in the JMP® Marketplace
Choose Language Hide Translation Bar
pmroz
Super User

Identify Same-Name Items in a List

I'm wondering if there's a slick way to identify items in a list that are duplicates of each other.  My list looks like this:

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

I want to return all of the positions of "Per" in the list.  I.e.

[3, 4, 5, 6, 7]

I can loop over the list to get the answer.  But is there another way that avoids the loop?

1 ACCEPTED SOLUTION

Accepted Solutions
stan_koprowski
Community Manager Community Manager

Re: Identify Same-Name Items in a List

Hi @pmroz 

You could use the Loc function--

 

loc(values, "Per" );

 

cheers,

Stan

 

//:*/

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

loc(values, "Per")

/*:

 

[3, 4, 5, 6, 7]

View solution in original post

6 REPLIES 6
txnelson
Super User

Re: Identify Same-Name Items in a List

Peter,

There might be a better way to do this,

(See Stan's response for the correct solution.)

but here is my solution created at the end of a long day.  It takes your Values matrix and creates an Associative array with an entry for each value in the Values matrix that has duplicate values and all of the positions found for the key.

Names Default To Here( 1 );

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

dt = New Table( "test", private, New Column( "val", character ) );
dt:val << set values( values );
array = Associative Array( values );
uniqs = array << get keys;
For Each( {vals}, uniqs,
	positions = dt << get rows where( :val == vals );
	If( Length( positions ) > 1,
		array << insert item( vals, positions ),
		array << remove item( vals )
	);
);
Close( dt, nosave );

 

Jim
stan_koprowski
Community Manager Community Manager

Re: Identify Same-Name Items in a List

Hi @pmroz 

You could use the Loc function--

 

loc(values, "Per" );

 

cheers,

Stan

 

//:*/

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

loc(values, "Per")

/*:

 

[3, 4, 5, 6, 7]

txnelson
Super User

Re: Identify Same-Name Items in a List

Good solution Stan.  Here is your solution incorporated into my code which checks for all repeating values.

Names Default To Here( 1 );

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

array = Associative Array( values );
uniqs = array << get keys;
For Each( {vals}, uniqs,
	positions = loc(values, vals);
	If( Length( positions ) > 1,
		array << insert item( vals, positions ),
		array << remove item( vals )
	);
);
Jim
jthi
Super User

Re: Identify Same-Name Items in a List

If you want only exact matches, before JM18 you could use Loc and in JMP18 Where()

Names Default To Here(1);

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

idx1 = Loc(values, "Per"); // Before JMP17
idx2 = Where(values == "Per"); // JMP18

show(idx1, idx2);

Also if you need even non-exact matches in JMP18, Where() is able to do that

Names Default To Here(1);

values = {"APerBC", "PerDEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

idx2 = Where(Contains(values, "Per")); // JMP18

show(idx2);
-Jarmo
ngambles
Level III

Re: Identify Same-Name Items in a List

Here is a solution that doesn't require writing any loops. This method works on your example, and also works on multiple, duplicate values without having to identify the duplicate values in the code. 

 

names default to here(1);

values = {"ABC", "DEF", "Per", "Per", "Per", "Per", "Per", "XYZ", "UVW"};

// make data table with values //
dt = new table("item table" /*, private*/);
dt << new column("Items", character, nominal, set values(values));


// identify the duplicate rows //
dt << Select duplicate rows( Match( :Items ) );


// if you also want the first of the duplicate values, otherwise skip the next two lines //
dt << Go To( :Items );
dt << Select All Matching Cells();


// save the selected row results //
dupLocations = dt << get selected rows();


// clean up the data table //
close(dt, no save);



show(dupLocations);




pmroz
Super User

Re: Identify Same-Name Items in a List

I thought loc() only worked on numbers.  DOH!  Great solutions.

Thanks all!

-Peter