• 全部
  • C#综合技术
  • C#互联网桌面应用
  • AppLauncher
  • WinForm&WPF
  • C#开发新技术
  • 问答

一个线程访问冲突的例子,为什么不 崩溃?

wugamp 2015-04-28 05:35:25
两个线程同时写一个变量,应该会 崩溃。但是下面的实验没有崩溃。请问怎么回事?
使用方法:启动程序后,textBox1里显示0,按BUTTON1,显示1,再按BUTTON2,则交替显示1和2,不崩溃。

public partial class Form1 : Form
{
Thread t1;
Thread t2;
private int g_var;
private bool bBtn1;
private bool bBtn2;

public Form1()
{
InitializeComponent();
}

public void thread1(object ob)
{
while(true)
{
if (bBtn1)
while (true)
g_var = 1;
Thread.Sleep(10);
}
}

public void thread2(object ob)
{
while (true)
{
if (bBtn2)
while (true)
g_var = 2;
Thread.Sleep(10);
}
}

private void Form1_Load(object sender, EventArgs e)
{
timer1.Start();
g_var = 0;
bBtn1 = false;
bBtn2 = false;
t1 = new Thread(thread1);
t1.Start(1);
t2 = new Thread(thread2);
t2.Start();
}

private void button1_Click(object sender, EventArgs e)
{
bBtn1 = true;
}

private void button2_Click(object sender, EventArgs e)
{
bBtn2 = true;
}

private void timer1_Tick(object sender, EventArgs e)
{
textBox1.Text = g_var.ToString();
}
}
...全文
300 点赞 收藏 17
写回复
17 条回复
切换为时间正序
当前发帖距今超过3年,不再开放新的回复
发表回复
引用 15 楼 wugamp 的回复:
请问怎样才能捕获导致崩溃的异常呢? 另外,我用写LOG文件的方式跟踪了执行过程,发现崩溃的时候,都是一个线程(A)执行到 一半的时候,被另外一个线程(B)打断了,等B执行完毕,A再继续执行完毕,然后崩溃! 当然,A和B会 读写一些全局变量,但现在看来这不是崩溃的原因。. 那么会不会是 A 和 B 共同调用了一些函数呢?
如果你想让别人给你罗列线程冲突的“所有”写法,你好用来发现你的代码问题,对不起,这种方法太不靠谱了。 你应该实际地调试到你的什么变量发生了冲突,而不是总是停留在猜测的层面。
回复
引用 3 楼 wugamp 的回复:
我想制造一个“线程访问公共变量导致崩溃”的例子,请指点,谢谢!
主要是你在顶楼问题中不谨慎地使用了“同时写一个变量,应该会 崩溃”的字眼。实际过于不及的结果往往都是一样的,只有“用户恰当”才能明白你的意思。 下面这两个程序都会抛出异常:
int k;
var y = new List<string> { "a", "b", "C", "D" };
var z = new List<string>();
ThreadPool.QueueUserWorkItem(h =>
{
    k = y.Count;
    for (var i = 0; i < k; i++)
    {
        z.Add(y[i]);
        Thread.Sleep(1000);
    }
});
ThreadPool.QueueUserWorkItem(h =>
{
    k = 40;
});
var y = new List<string> { "a", "b", "C", "D" };
var z = new HashSet<string>();
for (var k = 0; k < y.Count; k++)
{
    ThreadPool.QueueUserWorkItem(h =>
    {
        z.Add(y[k]);
    });
}
回复
wugamp 2015-05-04
请问怎样才能捕获导致崩溃的异常呢? 另外,我用写LOG文件的方式跟踪了执行过程,发现崩溃的时候,都是一个线程(A)执行到 一半的时候,被另外一个线程(B)打断了,等B执行完毕,A再继续执行完毕,然后崩溃! 当然,A和B会 读写一些全局变量,但现在看来这不是崩溃的原因。. 那么会不会是 A 和 B 共同调用了一些函数呢?
回复
十八道胡同 2015-04-30
多线程访问一个变量是不会崩溃的,崩溃的可能是有未捕获的异常
回复
十八道胡同 2015-04-30
引用 11 楼 wugamp 的回复:
我现在的程序有不到10个线程,有时会崩溃。而且崩溃时,必然是一个线程执行到一半时被 另一个 线程抢占了。 完整的代码比较复杂,没法贴出来。不过这些线程都调用了共同的函数,并且使用了共同的全局变量。 我用互斥方法把这些共同的函数、共同的全局变量保护起来之后,就没有崩溃。 现在我想专门便个小程序,研究崩溃的原因。 恳请大家帮助!
如果有崩溃,你应该全局捕捉异常,看崩溃的异常就是了
回复
失落的神庙 2015-04-30
引用 11 楼 wugamp 的回复:
我现在的程序有不到10个线程,有时会崩溃。而且崩溃时,必然是一个线程执行到一半时被 另一个 线程抢占了。 完整的代码比较复杂,没法贴出来。不过这些线程都调用了共同的函数,并且使用了共同的全局变量。 我用互斥方法把这些共同的函数、共同的全局变量保护起来之后,就没有崩溃。 现在我想专门便个小程序,研究崩溃的原因。 恳请大家帮助!
所以不是思路问题。 是代码问题。
回复
wugamp 2015-04-30
我现在的程序有不到10个线程,有时会崩溃。而且崩溃时,必然是一个线程执行到一半时被 另一个 线程抢占了。 完整的代码比较复杂,没法贴出来。不过这些线程都调用了共同的函数,并且使用了共同的全局变量。 我用互斥方法把这些共同的函数、共同的全局变量保护起来之后,就没有崩溃。 现在我想专门便个小程序,研究崩溃的原因。 恳请大家帮助!
回复
啊拉丁的鱼 2015-04-29
引用 4 楼 caozhy 的回复:
线程访问公共变量本身不会导致崩溃,只是可能导致数据不同步,结果不是预期而已。而且随机发生,不是必然发生。
大概就是这个意思
回复
线程本身就有各自的优先级,会根据优先级自动分配操作,如果你要是不做特殊处理,肯定不会崩溃。
回复
xian_wwq 2015-04-29
对基本类型的多线程操作,只是产生了“脏”数据而已
回复
qzyf1992 2015-04-29
线程是操作系统调度的操作系统只会在某个时间原点用一个线程做一件事,多核处理器除外,所以是不会崩溃的
回复
失落的神庙 2015-04-29
如果不理解楼上的话,我就用通俗的给你解释下。 就好比群*(pi) 后。 你不知道孩子是谁的。
回复
你把数值弄得大一点试试,可能会乱码,但不会崩溃
回复
threenewbee 2015-04-28
线程访问公共变量本身不会导致崩溃,只是可能导致数据不同步,结果不是预期而已。而且随机发生,不是必然发生。
回复
wugamp 2015-04-28
我想制造一个“线程访问公共变量导致崩溃”的例子,请指点,谢谢!
回复
tcmakebest 2015-04-28
只有在访问不在保护区域的内存才会崩溃, 同时写一个变量不使用排斥技术是允许的.
回复
bdmh 2015-04-28
仅对g_var修改,不会崩溃,只是g_var的值会比较混乱,可能不是你想要的值 当把值给g_var时,mov g_var,eax,eax是啥g_var就是啥
回复
相关推荐
发帖
C#
创建于2007-09-28

10.5w+

社区成员

.NET技术 C#
申请成为版主
帖子事件
创建了帖子
2015-04-28 05:35
社区公告

让您成为最强悍的C#开发者