std::greater<>와 std::less<>

김민수·2025년 1월 8일

C++

목록 보기
18/68

std::greater<>std::less<>는 C++ 표준 라이브러리의 <functional> 헤더에 정의된 함수 객체다. 이들은 비교 연산을 수행하는 데 사용되며, 특히 정렬이나 우선순위 큐와 같은 STL 컨테이너에서 유용하게 활용된다.


1. std::less<>

  • 기본적으로 STL 컨테이너에서 오름차순 정렬에 사용된다.
  • 두 값을 비교하여 "작은지(<)"를 판단한다.
  • 예를 들어, std::sort는 기본적으로 std::less<>를 사용하여 오름차순으로 정렬한다.
#include <functional> // std::less

int main() {
    std::vector<int> vec = {5, 3, 8, 1, 4};

    // 기본 정렬 (std::less<> 사용)
    std::sort(vec.begin(), vec.end(), std::less<>());

    for (int n : vec) {
        std::cout << n << " ";
    }
    return 0;
}

출력:

1 3 4 5 8


2. std::greater<>

  • 기본 정렬 순서를 반대로 뒤집어 내림차순 정렬을 수행한다.
  • 두 값을 비교하여 "큰지(>)"를 판단한다.
  • 우선순위 큐에서 큰 값이 우선이 되도록 할 때 사용된다.
#include <functional> // std::greater

int main() {
    std::vector<int> vec = {5, 3, 8, 1, 4};

    // 내림차순 정렬 (std::greater<> 사용)
    std::sort(vec.begin(), vec.end(), std::greater<>());

    for (int n : vec) {
        std::cout << n << " ";
    }
    return 0;
}

출력:

8 5 4 3 1


3. std::greater<>와 std::less<>를 직접 사용

이 함수 객체를 별도로 생성하여 비교 연산에 사용할 수 있다.

#include <functional> // std::greater, std::less

int main() {
    int a = 5, b = 3;

    std::greater<int> greaterFunc;
    std::less<int> lessFunc;

    std::cout << "Is 5 > 3? " << greaterFunc(a, b) << "\n"; // 1 (true)
    std::cout << "Is 5 < 3? " << lessFunc(a, b) << "\n";    // 0 (false)

    return 0;
}

출력:

Is 5 > 3? 1
Is 5 < 3? 0


4. 기본 데이터 타입

std::greater<>std::less<>는 기본 데이터 타입에서 문제없이 사용할 수 있다.

예시:

  • int, float, double, char, bool
int main() {
    std::greater<int> greaterInt;
    std::greater<double> greaterDouble;
    std::greater<char> greaterChar;

    std::cout << greaterInt(10, 5) << "\n";      // 1 (true)
    std::cout << greaterDouble(3.14, 2.71) << "\n"; // 1 (true)
    std::cout << greaterChar('b', 'a') << "\n";  // 1 (true)

    return 0;
}
  • char 타입은 ASCII 값을 기반으로 대소를 판단한다.
  • 명시적으로 타입을 지정하지 않더라도 컴파일러가 타입을 추론해서 동작한다.


5. 문자열(std::string)

std::string은 비교 연산자(>, <)를 지원하기 때문에, std::greater<>std::less<>로 문자열의 사전 순서 비교가 가능하다.

int main() {
    std::string str1 = "apple";
    std::string str2 = "banana";

    std::greater<std::string> greaterString;
    std::less<std::string> lessString;

    std::cout << greaterString(str1, str2) << "\n"; // 0 (false)
    std::cout << lessString(str1, str2) << "\n";    // 1 (true)

    return 0;
}

설명:

  • std::string은 사전순으로 비교된다.
  • "apple""banana"보다 작다고 판단된다.


6. 사용자 정의 데이터 타입

  • 사용자 정의 타입도 비교 연산자를 오버로드하거나 별도의 함수 객체를 제공하면 사용할 수 있다.
struct Person {
    std::string name;
    int age;

    // 비교 연산자 오버로드
    bool operator<(const Person& other) const {
        return age < other.age;
    }

    bool operator>(const Person& other) const {
        return age > other.age;
    }
};

int main() {
    std::vector<Person> people = {{"Alice", 30}, {"Bob", 25}, {"Charlie", 35}};

    // 나이를 기준으로 내림차순 정렬
    std::sort(people.begin(), people.end(), std::greater<Person>());

    for (const auto& person : people) {
        std::cout << person.name << " (" << person.age << ")\n";
    }

    return 0;
}

출력:

Charlie (35)
Alice (30)
Bob (25)


7. 포인터 타입

  • 포인터 타입도 비교 연산자를 지원하기 때문에 사용할 수 있다.
  • 일반적으로 포인터의 주소값을 기준으로 비교한다.
int main() {
    int a = 5, b = 10;
    int* ptr1 = &a;
    int* ptr2 = &b;

    std::greater<int*> greaterPointer;

    std::cout << greaterPointer(ptr1, ptr2) << "\n"; // 결과는 주소값에 따라 달라짐

    return 0;
}
profile
안녕하세요

0개의 댓글