2018년 11월 4일 일요일

std::call_once 와 std::once_flag

std::call_once 는 아래 C++11에서 추가되었는데 아래와 같은 정의를 가지고 있다.
1
2
3
// Defined in header <mutex>
template< class Callable, class... Args >
void call_once( std::once_flag& flag, Callable&& f, Args&&... args );
cs

여러 개의 스레드에서 호출될 때, 한 번만 호출되게 할 수 있다.

물론 멀티 스레드 환경이 아니더라도 아래와 같이 쓸 수도 있다.
Singleton 패턴에도 사용할 수 있겠고..

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
#include <iostream>
#include <mutex>
using namespace std;
 
class MrRobot
{
public:
    MrRobot(int serial) : serial_number_(serial) {};
 
    void PrintSerialNumber() 
    {
        std::call_once(once_flag_, [] 
        {
            cout << "MrRobot: ";
        });
 
        cout << serial_number_ << "\n";
    }
 
private:
    std::once_flag once_flag_;
    int serial_number_;
};
 
int main(void)
{
    MrRobot a(1);
    a.PrintSerialNumber();
    a.PrintSerialNumber();
 
    MrRobot b(2);
    b.PrintSerialNumber();
 
    return 0;
}
cs

위에 코드를 실행하면 결과는 아래와 같다.

MrRobot: 1
1
MrRobot: 2

디버깅 모드에서 once_flag_ 변수의 변화를 살펴보니 0x00000000 -> 0x00000002로
람다함수를 실행하면서 변경해준다.

그래서 memset 함수를 사용해서 저 변수를 다시 0으로 초기화하는 코드를 넣어보면
아래처럼 출력된다.

MrRobot: 1
MrRobot: 1
MrRobot: 2


댓글 없음:

댓글 쓰기

A*, JPS 길찾기 알고리즘 시뮬레이션 사이트

https://qiao.github.io/PathFinding.js/visual/ 길 찾기 알고리즘 시행 과정을 보여주는 사이트다. 링크 메모..