Operator Type:
Operator Scope of Action:
Operator Purpose:
Operator First Added:
Operator Last Altered:
Function [other Function type actions]
Item [operators of similar scope]
Data manipulation [other Data manipulation operators]
Baseline
9.5.0
Syntax note: Operators without any defined mandatory arguments may omit their empty closing parentheses
List.unique()
List.unique
This returns a List of the unique values in the list, as a sorted but de-duped list. Hitherto, de-duping required passing data into a Set-type attribute and back. Trailing parentheses are optional for this function.
Be aware that this function results in a case insensitive A-Z sort, thus not 'bee;ant;cow' as might otherwise be assumed (to get such an outcome see further below). For example, if $MyList is 'bee;ant;cow;bee':
$MyList = $MyList.unique;
results in a list value 'ant;bee;cow'.
The function can be chained with .sort-type actions and .reverse.
$MyList = $MyList("Another note").unique;
$SomeList = collect(children, $MyNumberList).unique.nsort;
$MyList = collect(children, $MyList).unique.reverse;
The last above sets $MyList to a list of all the unique, discrete, values to be found in $MyList in every child of the current note. Use with collect() or collect_if() to act on a particular attribute across a group of notes. If a collect() with query scope is the designator 'all' the result will be every discrete value for the referenced list attribute across the whole document.
This function does not apply to Set-type lists because Sets automatically de-duplicate items so are always a list of unique values.
De-duping a list whilst retaining original sort order
The basic method is this:
$MyList.each(anItem){
if(!$MyList2.contains(anItem)){
$MyList2+=anItem;
}
};
If is it desired to de-dupe $MyList back to itself, use a list-type variable:
var:list vList;
$MyList.each(anItem){
if(!vList.contains(anItem)){
vList+=anItem;
}
};
$MyList = vList;
A further consideration is whether the tested list's items are in varying case ('ant' vs. 'Ant' vs. 'ANT' etc.). For instance, to take a mixed case list with duplicates and end up with a de-duped all-lowercase version, use:
var:list vList;
$MyList.lowercase.each(anItem){
if(!vList.contains(anItem)){
vList+=anItem;
}
};
$MyList = vList;
Resulting order
From v9.5.0, .unique() preserves the order of elements in a list. Previously, the operator forced an A-Z order, but this was not ideal as one feature of List-type lists is that they allow duplicates do not auto-sort—unlike Set-type lists). Thus now:
"C:A;A;B".unique;
now returns "C;A;B" (previously it would have been "A;B;C", destroying the original ordering).