Last active
April 7, 2022 23:33
-
-
Save Porges/411df8738f82266bb6d9b1d83a2441cf to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <atomic> | |
#include <string> | |
#include <chrono> | |
#include <iostream> | |
std::string GetValueFromSomewhere() | |
{ | |
auto now = std::chrono::system_clock::now(); | |
return std::to_string(now.time_since_epoch().count()); | |
} | |
class Foo { | |
std::atomic<std::string*> var_; | |
public: | |
Foo() | |
: var_{nullptr} | |
{} | |
~Foo() { | |
delete var_.load(); | |
// note that this invalidates any existing references, | |
// if you want to be really safe then return by value from the method | |
} | |
const std::string& LoadCachedOrFresh() | |
{ | |
std::string* result = var_.load(); | |
if (result) | |
{ | |
return *result; | |
} | |
else | |
{ | |
std::string* methodResult = new std::string(GetValueFromSomewhere()); | |
std::string* expected = nullptr; | |
if (!var_.compare_exchange_strong(expected, methodResult)) | |
{ | |
// someone already wrote the variable, the result is in 'expected' | |
delete methodResult; | |
return *expected; | |
} | |
else | |
{ | |
return *methodResult; | |
} | |
} | |
} | |
}; | |
int main() { | |
Foo f; | |
std::cout << f.LoadCachedOrFresh() << '\n'; | |
std::cout << f.LoadCachedOrFresh() << '\n'; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment