C++ 原子增量和返回计数器

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/41206861/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-28 15:26:09  来源:igfitidea点击:

atomic increment and return counter

c++multithreading

提问by Anonymous Entity

Trying to make a unique id generating function, and came up with this:

试图制作一个独特的 id 生成函数,并想出了这个:

std::atomic<int> id{0};
int create_id() {
    id++;
    return id.load();
}

But I assume it's possible for that function to return the same value twice, right? For example, thread A calls the function, increments the value, but then halts while thread B comes in and also increments the value, finally A and B both return the same value.

但我认为该函数有可能两次返回相同的值,对吗?例如,线程 A 调用该函数,递增值,但随后在线程 B 进入并递增值时暂停,最后 A 和 B 都返回相同的值。

So using mutexes, the function might look like this:

因此,使用互斥锁,该函数可能如下所示:

std::mutex mx;
int id = 0;
int create_id() {
    std::lock_guard<std::mutex> lock{mx};
    return id++;
}

My question: Is it possible to create the behavior of spawning unique int values from a counter using only atomics? The reason I'm asking is because I need to spawn a lot of id's, but read that mutex is slow.

我的问题:是否可以仅使用原子来创建从计数器生成唯一 int 值的行为?我问的原因是因为我需要生成很多 id,但是读到互斥锁很慢。

回答by Jarod42

Simply use:

只需使用:

std::atomic<int> id;

int create_id() {
    return id++;
}

See http://en.cppreference.com/w/cpp/atomic/atomic/operator_arith

请参阅http://en.cppreference.com/w/cpp/atomic/atomic/operator_arith

回答by Pete Becker

Your two code snippets do two different things.

你的两个代码片段做了两件不同的事情。

id++;
return id.load();

that code increments id, then returns the incremented value.

该代码递增id,然后返回递增的值。

std::lock_guard<std::mutex> lock{mx};
return id++;

that code returns the value beforethe increment.

该代码返回增量的值。

The correct code to do what the first tries to do is

做第一个尝试做的正确代码是

return ++id;

The correct code to do what the second does is

执行第二个操作的正确代码是

return id++;