모두의 코드
C++ 레퍼런스 - std::generate (<algorithm>)

작성일 : 2020-09-23 이 글은 181 번 읽혔습니다.

아직 C++ 에 친숙하지 않다면 씹어먹는 C++ 은 어때요?

generate

<algorithm> 에 정의됨

// C++ 17 이하 에서는 costexpr 함수가 아님
template <class ForwardIt, class Generator>
constexpr void generate(ForwardIt first, ForwardIt last, Generator g);  // (1)

template <class ExecutionPolicy, class ForwardIt, class Generator>
void generate(ExecutionPolicy&& policy, ForwardIt first, ForwardIt last,
              Generator g);  // (2)

범위 내에 원소들을 인자로 전달된 함수에서 생성된 값으로 채운다

generate 함수는 first 부터 last 전 까지의 원소들의 값에 g() 의 리턴값으로 복사합니다.

  1. first 부터 last 까지 원소들에 함수 객체 g 를 실행한 값을 복사합니다.

  2. (1) 과 비슷하지만, 실행 방식을 받을 수 있는데 전달하는 policy 의 경우 반드시 std::is_execution_policy_v<std::remove_cvref_t<ExecutionPolicy>> 를 만족해야 한다.

인자들

  • first, last: 생성된 값을 대입할 원소들의 범위를 나타낸다.

  • policy : 사용할 실행 방식

  • g : 실행할 생성 함수. 참고로 전달할 함수는 Ret fun(); 와 같은 꼴이어야만 하고, Ret 의 경우 반드시 ForwardIt 를 역참조한 객체에 대입 가능해야만 한다.

리턴값

없음

구현 예시

template <class ForwardIt, class Generator>
void generate(ForwardIt first, ForwardIt last, Generator g) {
  while (first != last) {
    *first++ = g();
  }
}

실행 예제

#include <algorithm>
#include <iostream>
#include <vector>

int f() {
  static int i = 1;
  return i++;
}

int main() {
  std::vector<int> v(5);
  std::generate(v.begin(), v.end(), f);

  std::cout << "v: ";
  for (auto iv : v) {
    std::cout << iv << " ";
  }
  std::cout << "\n";

  // 참고로 아래와 같이 lambda 의 capture 에서 객체를 생성하는 경우, 해당 람다
  // 객체와 함께 생성된 것이라 간주하면 되고, 람다가 소멸 되기 전 까지 계속
  // 유지됩니다. 물론 해당 capture 역시 값을 캡쳐하는 것이므로 mutable 람다가
  // 아니면 해당 값을 수정할 수 없습니다.
  //
  // std::iota(v.begin(), v.end(), 0); 와 동일한 문장.
  std::generate(v.begin(), v.end(), [n = 0]() mutable { return n++; });

  std::cout << "v: ";
  for (auto iv : v) {
    std::cout << iv << " ";
  }
  std::cout << "\n";
}

실행 결과

v: 1 2 3 4 5
v: 0 1 2 3 4

연관된 함수

  • fill : 범위 내에 원소에 주어진 값을 대입합니다.

  • generate_n : 범위 안의 처음 N 개의 원소들에 생성된 값을 대입합니다.

  • iota : 등차수열을 생성하여 원소들에 대입합니다.

첫 댓글을 달아주세요!
프로필 사진 없음
강좌에 관련 없이 궁금한 내용은 여기를 사용해주세요