线程如何访问全局变量,线程可以通过进程的全局变量

http://www.itjxue.com  2023-01-08 04:19  来源:未知  点击次数: 

关于线程并发访问全局变量问题

我怎么觉得都可能呢?

假设线程x和y同时执行,x和y可随时被抢占,a的初始值为1

A:3, 2

y先执行++a,a为2;

y再执行printf,a入栈,在打印到终端之前切换到x

x执行++a,a为3;

x执行printf,输出3;再切换到y

y执行打印,输出2

B:2 3

x先执行++a,a为2;

x再执行printf,输出2;切换到y

y执行++a,a为3;

y执行printf,输出3;

C:3 3

x先执行++a,a为2;切换到y

y执行++a,a为3;

y执行printf,输出3;切换到x

x执行printf,输出3

D:2 2

类似C,a的初始值为0即可

这里关键有两点:

(1)两个线程可随时被抢占

(2)++a和printf不是原子指令,可随时被打断;特别注意函数printf,a作为参数压栈后,a再变化则不会影响输出(printf实际打印的是压栈的参数,是值拷贝的栈变量)

TCL中如何在子线程中访问全局函数或者全局变量

set procedure to kk 是打开过程文件

public x,y 定义全局变量,全局有效

private 是在过程中屏蔽public定义的变量,即私有变量,离开过程,就会实效。

local 定义局部变量,作用域只在本过程。

x=30 是赋值语句,将30赋给x

public x,y 定义全局变量

set proc to kk 打开过程文件

x=20 全局变量赋值

y=50

do a1 执行过程a1

?x,y

set proc to

return

*过程序文件kk.prg

proc a1

private x 定义私有变量,屏蔽调用过程的x

x=30 x=30

local y 定义局部变量,y为逻辑假

do a2 执行a2

?x,y

return

proc a2

x="kkk" x赋值,x如果脱离a2过程,x变成全局变量,即x=20

y="mmm" y从a1过程出来,变成全局变量,重新赋值“mmm”

return

看着我的解释导顺序,就会明白的

线程之间如何调用变量

如楼上所说,线程的局部变量是无法互相调用的,可以声明一些全局变量。但需要在声明的时候bool前面加volatile,如果不加,很有可能你在2个线程中访问同一个变量时,2个变量的值是不一样的,因为编译器会进行优化。简单点说就是编译器在进行2个线程的处理时,都将该变量读入一个临时内存保存起来,在使用时直接使用,因为这样速度更快,而在变量前加volatile的目的是告诉编译器不要优化这个变量,每次使用他时,都从寄存器中读取,所以一当这个变量的值有变动时,只要有对它进行访问,都能拿到最新的数据。

如volatile bool IsNextData;

否则编译器会进行优化

IsNextData直接从寄存器中取值,而不访问内存。

而你在另一个线程中改变的事IsNextData内存中的值。

跟踪也是访问内存的值。

给你百科对volatile的解释:

多线程对全局变量的操作

1. 初始化的时候, 如果线程A执行完毕的时候, 线程B还没有运行(相信这个时候C还没有创建), 那么g_str肯定存的是初始化时读取的值.

线程B要按button才调用, 如果一直没有按button, 就一直没有调用. 所以正常情况下你的程序都只有运行线程C, 你可以确认一下:

a) 初始化后线程A, 有没有结束

b) 不按button, g_str的赋值是否正确? 如果不按button都不正确, 那么你的线程C的赋值本身就有问题. 注意看你怎么判断赋值成功, 或者赋值错了? 在什么时间点判断g_str的赋值出错.

2. 你的情况线程B是随机发生的, 与线程C有冲突, 如果只是为了访问不冲突的话, 一般为g_str加个互斥就可以. 对g_str有特殊的使用点要求(对读取的时间点有要求)的话, 才要考虑同步的问题.

(责任编辑:IT教学网)

更多

推荐Dreamweaver教程文章