Usage of std::unique in C++

The std::unique can be used in two ways as shown below:

  • For Comparing elements using ==
  • For Comparing using a pre-defined function

1. Comparing elements using ==:

Syntax:

 ForwardIterator unique (ForwardIterator first, ForwardIterator last, BinaryPredicate Pred);

Here, the first and last are the same as the previous case.

Pred: Binary function that accepts two elements in the range as argument, and returns a value convertible to bool. The value returned indicates whether both arguments are considered equivalent(if true, they are equivalent and one of them is removed). The function shall not modify any of its arguments. This can either be a function pointer or a function object.

Return Value: It returns an iterator to the element that follows the last element not removed. The range between the first and this iterator includes all the elements in the sequence that were not duplicates and hence not removed.

Below is the implementation of the above method:

C++




// C++ program to demonstrate the use of std::unique
#include <algorithm>
#include <iostream>
#include <vector>
using namespace std;
int main()
{
    vector<int> v = { 1, 1, 3, 3, 3, 10, 1, 3, 3, 7, 7, 8 };
 
    vector<int>::iterator ip;
 
    // Using std::unique
    ip = std::unique(v.begin(), v.begin() + 12);
    // Now v becomes {1 3 10 1 3 7 8 * * * * *}
    // * means undefined
 
    // Resizing the vector so as to remove the undefined
    // terms
    v.resize(std::distance(v.begin(), ip));
 
    // Displaying the vector after applying std::unique
    for (ip = v.begin(); ip != v.end(); ++ip) {
        cout << *ip << " ";
    }
 
    return 0;
}


Output

1 3 10 1 3 7 8 

Here, in this vector, all the sub-groups having consecutive duplicate elements has been reduced to only one element. Note that it doesnot matter whether the same element is present later on as well, only duplicate elements present consecutively are handled by this function.

2. Comparing using a pre-defined function:

Syntax:

ForwardIterator unique (ForwardIterator first, ForwardIterator last);

first: Forward iterator to the first element in the container.
last: forward iterator to the last element in the container.

Return Value: It returns an iterator to the element that follows the last element not removed. The range between first and this iterator includes all the elements in the sequence that were not duplicates and hence not removed.

Below is the implementation of the above method:

C++




// C++ program to demonstrate the use of std::unique
#include <algorithm>
#include <iostream>
#include <string>
using namespace std;
 
// Defining the BinaryFunction
bool Pred(char a, char b)
{
    // Checking if both the arguments are same and equal
    // to 'G' then only they are considered same
    // and duplicates are removed
    if (a == b && a == 'G') {
        return 1;
    }
    else {
        return 0;
    }
}
int main()
{
    // Declaring a string
    string s = "You arre vvvisiting GGGGFGGGG";
 
    // Using std::unique to remove the consecutive
    // G in the word
    auto ip = std::unique(s.begin(), s.end(), Pred);
 
    // Displaying the corrected string
    cout << string(s.begin(), ip);
    return 0;
}


Output

You arre vvvisiting GFG

Here, we have manipulated the binary function in such a way that only if two G are passed as arguments, then only they will be considered as same, and if any other character is present consecutively, then it will remain unaffected, and will not be removed (like r in arre, v in visiting).

Interesting Point:

The std::unique function can be used in combination with the std::erase function to remove consecutive duplicate elements from a sorted container.

vec.erase(unique(vec.begin(), vec.end()), vec.end());

std::unique in C++

In C++, std::unique is used to remove duplicates of any element present consecutively in a range[first, last). It performs this task for all the sub-groups present in the range having the same element present consecutively.

  • It does not delete all the duplicate elements, but it removes duplicacy by just replacing those elements with the next element present in the sequence which is not duplicate to the current element being replaced. All the elements which are replaced are left in an unspecified state.
  • Another interesting feature of this function is that it does not change the size of the container after deleting the elements, it just returns a pointer pointing to the new end of the container, and based on that we have to resize the container or remove the garbage elements.

Time Complexity: O(N)
Space Complexity: O(1)

Similar Reads

Usage of std::unique in C++

The std::unique can be used in two ways as shown below:...

Where std::unique can be used?

...