2010-05-17 69 views
5

我正在使用下面的代码进行线程安全访问变量。线程安全get(访问器方法)

int gnVariable; 

void getVariableValue(int *pnValue) 
{ 
    acquireLock(); //Acquires the protection mechanism 
    *pnValue = gnVariable; 
    releaseLock(); //Releasing the protection mechanism 
} 

我想我API的签名更改为更方便用户

int getVariableValue(void); 

我应该如何重写功能 - 使得API的用户不必理会锁定/解锁细节?

+0

我不明白你的问题。您建议的API都不提供锁定细节。 – zvrba 2010-05-17 06:24:21

+0

如果更改为第二个版本 - int getVariable(void) - ,API的用户将不得不手动释放/解锁信号量。如果你不这样做Samuel和Naveen建议 – sonofdelphi 2010-05-17 07:51:01

回答

9

既然你给了C++一个选项,你可以包装互斥锁/解锁。然后,您可以直接返回值:

class lock_wrapper 
{ 
public: 
    lock_wrapper() 
    { 
     acquireLock(); 
    } 
    ~lock_wrapper() 
    { 
     releaseLock(); 
    } 
}; 

int getVariableValue() 
{ 
    lock_wrapper lw; 
    return gnVariable; 
} 

这也会派上用场,如果你需要做一个锁定/周围的代码,可以抛出异常解锁。

+0

在C中做同样的想法吗? – sonofdelphi 2010-05-17 06:04:38

+1

我曾经为此使用计数信号量。在一些实时操作系统中计算信号量支持原子操作的getValue()操作。 – sonofdelphi 2010-05-17 06:05:58

+0

@sonofdelphi - 对于C,你应该使用Naveen的答案。 – 2010-05-17 06:06:01

8

您返回本地变量的副本。喜欢的东西:

int getVariableValue(void) 
{ 
    int local= 0; 
    acquireLock(); 
    local = gnVariable; 
    releaseLock(); 
    return local; 
} 

作为一个侧面说明,最好是RAII原则锁定,而不是acquireLockreleaseLock方法。

+0

本地副本似乎有点不雅。 :)没有其他的去? – sonofdelphi 2010-05-17 06:07:06

+0

@sonofdelphi:@R Samuel Klatchko是一个更好的解决方案。我只是想演示如何使用本地副本来做到这一点。 – Naveen 2010-05-17 06:08:59

+2

@sonofdelphi:局部变量应该由一个体面的编译器进行优化 - 它会将'gnVariable'直接复制到返回值位置。 – caf 2010-05-17 06:24:57