大家来来看看这段简单代码 thredm 函数以开始会执行几次? 并说明一下原因

风平心境 2010-07-15 09:13:02
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;

namespace ProductAndConsume
{
class Program
{
static void Main(string[] args)
{
Thread t = new Thread(new ThreadStart(thredm));
t.Start();
Thread t1 = new Thread(new ThreadStart(thredm1));
t1.Start();
Thread t3 = new Thread(new ThreadStart(thredm));
t3.Start();
}
static object obj = new object();
static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
Console.ReadLine();
}
Console.WriteLine("open lock");
Console.ReadLine();
}
}

static void thredm1()
{
while (true)
{
obj = new object();
Thread.Sleep(100);
Console.WriteLine("modify object");
}
}
}
}



...全文
253 33 打赏 收藏 转发到动态 举报
写回复
用AI写文章
33 条回复
切换为时间正序
请发表友善的回复…
发表回复
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 29 楼 angel6709 的回复:]

static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
Console.ReadLine();
}
Console.WriteLine("open lock");
Console.ReadLine();
}
}
--……
[/Quote]
真的谢谢你!
lock(obj) 并不能保证obj被覆盖.只能保证 obj里面的成员不能被修改.我试过了哦.继承object 加一属性id 如果在t1修改 obj的id属性就不让修改.如果是new object 覆盖原来的obj是允许的.这样就导致lock(obj)的区段可以让别的线程进来的. 因此微软的那句也不完全正确 结贴了.
angel6709 2010-07-15
  • 打赏
  • 举报
回复
obj在th中被lock住了
但是为什么th1中还能修改obj是正确的。。。。

lock 關鍵字可保證有執行緒在關鍵區段時,絕對不會有任何其他執行緒同時也進入這個關鍵區段執行。如果其他執行緒嘗試進入已鎖定的程式碼,它將會等候、封鎖,直到該物件被釋出

在C#中一个obj被创建就只能等着被回收,自己不会释放。。。,。。
虽然obj指向了新的Object,但是原来的obj并没有释放。

wxm3630478 2010-07-15
  • 打赏
  • 举报
回复
静态变量能用lock()锁的到吗??
angel6709 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 28 楼 guankai 的回复:]
引用 27 楼 angel6709 的回复:

static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
……

Console.ReadLine(); 会堵塞线程的.
[/Quote]

会阻塞当前线程,正好给其他线程时间去执行,
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 27 楼 angel6709 的回复:]

static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
……
[/Quote]
Console.ReadLine(); 会堵塞线程的.
angel6709 2010-07-15
  • 打赏
  • 举报
回复
static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
Console.ReadLine();
}
Console.WriteLine("open lock");
Console.ReadLine();
}
}
-----》》》》》


static void thredm()
{
lock(obj)
{
while (true)
{

Console.WriteLine("t1 lock");
Console.ReadLine();

Console.WriteLine("open lock");
Console.ReadLine();
}
}
}

这样试试
angel6709 2010-07-15
  • 打赏
  • 举报
回复
static void thredm()
{
while (true)
{
lock(obj)
{
Console.WriteLine("t1 lock");
Console.ReadLine();
}
Console.WriteLine("open lock");
Console.ReadLine();

}
}



是在这个短短的没有lock的时间改的
铛铛 2010-07-15
  • 打赏
  • 举报
回复
明白LZ的意思
obj在th中被lock住了
但是为什么th1中还能修改obj
对吗?
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 24 楼 angel6709 的回复:]

C# code

using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;

namespace ProductAndConsume
{
class Program
{
static int item=10;
static ……
[/Quote]
非常感谢你的回答.不要被的命名空间给误导了.那是我懒的新建文件,就在生产和消费的例子里面现改的.
我只是想知道为什么:
" lock(obj) 为什么不能保证 obj不被别的线程修改呢?"我上面的lock代码区段的确进去两个线程了啊??这就是我心中的疑问.消费和生产者这个问题我理解.
angel6709 2010-07-15
  • 打赏
  • 举报
回复

using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;

namespace ProductAndConsume
{
class Program
{
static int item=10;
static void Main(string[] args)
{
Thread t = new Thread(new ThreadStart(Pro));
t.Start();
Thread t1 = new Thread(new ThreadStart(Modify));
t1.Start();
Thread t3 = new Thread(new ThreadStart(Con));
t3.Start();
}
static Object obj =new Object();
static void Pro()
{
while (true)
{
lock (obj)
{
if (item<10)
{
item++;
Console.WriteLine("Pro one item,cur item count:" + item.ToString() + " lock is :" + obj.GetHashCode().ToString());
Thread.Sleep(1000);
}
}
Thread.Sleep(100);

}
}

static void Con()
{
while (true)
{
lock (obj)
{
if (item >0)
{
item--;
Console.WriteLine("Con one item,cur item count:" + item.ToString()+" lock is :"+obj.GetHashCode().ToString());
}

}
Thread.Sleep(100);
}
}

static void Modify()
{
while (true)
{
obj = new Object();
Console.WriteLine("obj Modifyed to:" + obj.GetHashCode().ToString());
Thread.Sleep(1000);
}
}
}
}




生产者消费者,这个比较说明问题
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 12 楼 sp1234 的回复:]

给你改一下,你再测试呢?C# code
static void Main(string[] args)
{
Thread t = new Thread(new ThreadStart(thredm));
t.Start();
Thread t1 = new Thread(new Thread……
[/Quote]
一样的结果.t3 在t 没有释放的时候还是进去lock里面了
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 20 楼 sp1234 的回复:]

引用 17 楼 guankai 的回复:
我只是证明我自己理解lock 没有.没别的意思 我肯定是测试有疑问,很努力的google后才来问的.


很少有写一个测试就能验证设计的。我们写一个只有几十行的小程序,在同一天内针对它的单元测试往往要写3个以上,而整个项目中能够测试到这个几十行小程序的单元测试不下几十个,这样才能对程序有点安全感。

当你写的系统需要高效、并行,那么更是如此。……
[/Quote]
呵呵.我想的并没有那么复杂,只是解掉自己心中的疑惑而已.既然疑问自己当然要自己写以段代码证明一下为什么会这样而已.可是执行结果并非自己所想,翻了十几页的google才来问人.如果解决了当然开心.没解决还不是挂咱心上.
风平心境 2010-07-15
  • 打赏
  • 举报
回复
问题是lock(obj) 为什么不能保证 obj不被别的线程修改呢?
  • 打赏
  • 举报
回复
[Quote=引用 17 楼 guankai 的回复:]
我只是证明我自己理解lock 没有.没别的意思 我肯定是测试有疑问,很努力的google后才来问的.
[/Quote]

很少有写一个测试就能验证设计的。我们写一个只有几十行的小程序,在同一天内针对它的单元测试往往要写3个以上,而整个项目中能够测试到这个几十行小程序的单元测试不下几十个,这样才能对程序有点安全感。

当你写的系统需要高效、并行,那么更是如此。会写程序不算任何本事,会写好测试程序才是本事。
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 16 楼 angel6709 的回复:]

t进去了 t1修改obj 就修改不了
[/Quote]
呵呵,看来很多人跟我的想法一样,可是并非如此,其中肯定有蹊跷
  • 打赏
  • 举报
回复
还可以做第三个测试:
        static void thredm1()
{
Thread.Sleep(100);
while (true)
{
obj = new object();
Thread.Sleep(100);
Console.WriteLine("modify object");
}
}
风平心境 2010-07-15
  • 打赏
  • 举报
回复
[Quote=引用 14 楼 sp1234 的回复:]

引用 5 楼 guankai 的回复:
问题来了.这是microsoft的说明.lock区域两个线程都进去了.

所以遇到烂程序,用测试来说明,不要玩理论。你测试了,于是证明microsoft的说明没错。
[/Quote]
我只是证明我自己理解lock 没有.没别的意思 我肯定是测试有疑问,很努力的google后才来问的.
angel6709 2010-07-15
  • 打赏
  • 举报
回复
t进去了 t1修改obj 就修改不了
  • 打赏
  • 举报
回复
哦,当然你原来的测试也很有意义,两个测试放在一起更能说明问题。
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 guankai 的回复:]
问题来了.这是microsoft的说明.lock区域两个线程都进去了.[/Quote]

所以遇到烂程序,用测试来说明,不要玩理论。你测试了,于是证明microsoft的说明没错。
加载更多回复(13)
代码转载自:https://pan.quark.cn/s/11d565366452 【USB转I2C/IIC适配器上位机应用程序】是一种针对I2C(Inter-Integrated Circuit)通信协议而构建的工具,其通过USB端口将个人计算机转变为能够与I2C设备进行交互的控制器。该适配器使开发人员与工程师能够便捷地对遵循I2C协议的芯片执行读取和写入任务,因此在硬件构建和测试阶段能够显著提升效率,对于核实I2C接口芯片的工作性能具有特别的价值。 I2C协议是由飞利浦(现NXP半导体)于1980年代初创立的一种双线式串行总线,其目的是用于连接微控制器及其他外围设备。该协议仅需两条信号线(SDA - 数据线,SCL - 时钟线)即可完成多设备间的通信,大幅度削减了电路板上的布线需求,从而降低了生产成本。I2C协议提供多种速度等级,涵盖标准模式(100kbps)、快速模式(400kbps)以及高速模式(3.4Mbps),旨在满足不同场景下的应用要求。 Ginkgo USB转I2C适配器是这项技术的具体应用实例,它提供了一个物理接口,用于将USB端口转换为I2C端口。适配器内部装配有一个微控制器单元,该单元负责处理从USB到I2C的信号转换,并且通过USB线路向计算机传输信息,同时接收来自计算机的指令以操控I2C总线。这种设计使用户无需具备深厚的硬件知识,仅需借助上位机软件即可实现对I2C设备的操控。 Ginkgo I2C Adapter Classic是与该适配器相配套的软件,通常包含以下几项核心功能: 1. 设备识别:自动检测并建立与USB转I2C适配器的连接。 2. 总线探查:扫描I2C总线上所连接的设备地址,有助于准确定位设备的位置。 3. 读写指令...
代码转载自:https://pan.quark.cn/s/4c053f9292d9 在Android应用程序的设计与实现过程中,有时需要借助C或C++语言所具备的高性能特点,此时就必须借助Android Studio的NDK(Native Development Kit)工具来对C/C++代码进行编译,进而生成SO(Shared Object)动态链接库文件。本篇文章将详尽阐述在Android Studio环境下如何执行这一流程。 我们首先需要掌握Android Studio项目的基本组织架构。在Android Studio的`app`文件夹内,存在一个名为`src`的子文件夹,该文件夹通常包含了`main`以及其他相关源代码目录。在`main`文件夹中,除了我们常见的`java`文件夹外,还设立了一个`jniLibs`文件夹,此文件夹专门用于存储SO文件。除此之外,还有一个`jni`文件夹,它是用来存放C/C++源代码的地方。 为了实现C/C++代码的编写与编译,我们必须在`build.gradle`文件中配置NDK的支持。打开`app/build.gradle`文件,在`defaultConfig`部分中嵌入以下内容: ```groovy externalNativeBuild { ndkBuild { path src/main/jni/Android.mk } } ``` 这段内容明确指示Android Studio去何处寻找`Android.mk`文件,该文件是一种Makefile的变体,主要用于设定编译规则和编译目标。 接下来,我们需要创建`Android.mk`文件。在这个文件中,我们将明确指定源代码文件、编译选项以及要生成的库名称。一个基础的...
内容概要:本文围绕麦克斯韦旋度方程的差分形式在平面极化磁场中的应用展开深入研究,并通过Matlab代码实现相关数值仿真。研究的核心是将经典的麦克斯韦方程组转化为适用于数值计算的有限差分格式,构建离散化数学模型,进而模拟和分析平面极化条件下磁场的空间分布特征与时间演化规律。文中系统阐述了差分方法的理论基础与数学推导过程,详细说明网格划分、边界条件设定及迭代求解策略,最终利用Matlab编程实现电磁场的可视化仿真,有效验证了差分方法在求解复杂电磁场问题中的准确性与可行性。该研究不仅加深了对电磁波传播机理的理解,也为电磁器件的设计优化与工程仿真提供了可靠的数值分析手段。; 适合人群:具备电磁场与电磁波理论基础,熟悉偏微分方程数值解法,且掌握Matlab编程技能的电气工程、物理学、应用数学等领域的研究生、科研人员及工程技术人员。; 使用场景及目标:①深入掌握麦克斯韦旋度方程的有限差分法基本原理及其在二维平面磁场仿真中的具体实施步骤;②学习如何利用Matlab进行电磁场问题的建模、编程求解与结果可视化;③为后续开展更复杂的电磁兼容、天线设计或光子晶体等领域的数值模拟研究奠定坚实的技术基础。; 阅读建议:建议读者结合经典电磁场理论教材,透彻理解麦克斯韦方程组的物理内涵,然后循序渐进地跟进文中的差分格式推导过程,务必动手复现并调试所提供的Matlab代码,通过调整参数观察仿真结果的变化,从而深刻领悟数值方法的实质与应用技巧。

111,129

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Creator Browser
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

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

试试用AI创作助手写篇文章吧