delphi 怎么实现多线程的同步

bbc9527 2013-06-06 01:55:37
正在写一个程序
涉及到多线程同步的问题
具体的过程可以抽象为这样(线程A和B都不是主线程,是主线程开启的)
线程A 获取事物C的坐标变量M 这个坐标第一次设置为0 即M(初始)=0 (后面设置为从线程B中处理后的数据。)事物A先判断线程B是否启动,如果没启动则启动线程B 根据事物C的坐标 执行操作A的动作,接着执行操作B的动作 。[动作B的操作可以对事物C进行缓慢消除。比如inc(事物C)]
循环执行线程A的动作直到线程退出。
线程B 判断事物C是否存在,不存在则遍历数据,获取事物新C的坐标,并且存储到 事物C坐标的变量M当中 即 M=新获取坐标(C)
执行操作B的动作。
动作B的操作可以对事物C进行缓慢消除。比如inc(事物C) 当事物C的某个数据=0的时候 C 就被消除了。
循环执行线程B的动作直到线程退出。
现在的问题就是 事物C的坐标变量M 同时被两个线程操作 而且中间还有很多的其他步骤,
我用了很多方法要么线程 堵塞 ,要么线程无法同步

请问应该用什么方式同步?怎么同步?
伪代码 --不知道是不是可以这么说
创建线程A
1、M=线程B中获得的M(第一次为0,后面为线程B中获得)
2、判断(线程B是否启动)
3、没有启动 则启动线程B
4、执行动作A(M)
5、执行动作B(inc(事物C))
6、回到1 直到线程A退出
创建线程B
1、判断是否存在(事物C)
2、不存在则创建(事物C)
3、M=得到坐标(事物C)
4、执行动作B(inc(事物C))
5、回到1 直到线程B退出
如何顺利的同步这两个线程?我用了
EnterCriticalSection(My);
try
finally
LeaveCriticalSection(My); //离开临界区
end;
结果线程B被阻塞了。。





...全文
773 34 打赏 收藏 转发到动态 举报
写回复
用AI写文章
34 条回复
切换为时间正序
请发表友善的回复…
发表回复
  • 打赏
  • 举报
回复
支持一 下~
bbc9527 2013-06-12
  • 打赏
  • 举报
回复
楼上 虽然给的语言不同 但是思路是对的 问题已经解决但是楼上 还是很热心 给分给你
MoreWindows 2013-06-09
  • 打赏
  • 举报
回复
楼主参考下《秒杀多线程第十篇 生产者消费者问题》 http://blog.csdn.net/morewindows/article/details/7577591
无聊找乐 2013-06-07
  • 打赏
  • 举报
回复
Delphi!? 难道是我眼花了? 现在还有人在搞delphi? 真是让人怀念啊~~~~
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 21 楼 JohnYale 的回复:
[quote=引用 14 楼 bbc9527 的回复:] [quote=引用 13 楼 JohnYale 的回复:] 线程同步不难,但很麻烦。 同步对象除了临界区之外,还有互斥、事件、信号量等,按照不同的要求合理选择才行。 你的问题我简化了一下,不知与你原意相符吗 m给A消费,消费完了再生产 c给B消费,消费完了再生产 问一下 m、c的生产有关系吗?似乎没关系---属于一个结构体啊 怎么没有关系 你看过代码么 但你在后面说的,似乎是m和c又要同时生产。
m和c都是一个结构体的数据 代表了这个结构的两个属性 对于生产这个结构体来说只要C消费完就可以开始 M是否消费完都不用考虑 但是M是必须要给A消费的不消费的就是程序的缺陷不能实现 本来的功能 还有补充一点 A也是要消费c的A消费的是两个 这样消费C可以加速 也就加速了 结构体的生产。 [/quote] 无语啊 我问的是 ‘m、c的生产有关系吗’ 你回答‘属于一个结构体啊 ’ 属于一个结构体是你自己定义的啊 必要时可以改嘛[/quote] 当然有关系了 比如一个数据库的一个记录 (学号 身份证号 什么的)怎么没关系? 只不过这里抽象了而已变成一个结构的两个数据 你连起码的逻辑方式都没想明白 如果这个问题具体化的话你可以想象 多线程查询计算一个数据库里面的数据 里面的有些数据是处理的快的有些慢,有些关键有些不关键 分成几个线程处理同时,这样可以快速的解决,但是数据在处理过程中没有存储好 定义全局变量或者局部变量就导致混乱了 都不知道你怎么去思考这个问题的
JohnYale 2013-06-07
  • 打赏
  • 举报
回复
引用 14 楼 bbc9527 的回复:
[quote=引用 13 楼 JohnYale 的回复:] 线程同步不难,但很麻烦。 同步对象除了临界区之外,还有互斥、事件、信号量等,按照不同的要求合理选择才行。 你的问题我简化了一下,不知与你原意相符吗 m给A消费,消费完了再生产 c给B消费,消费完了再生产 问一下 m、c的生产有关系吗?似乎没关系---属于一个结构体啊 怎么没有关系 你看过代码么 但你在后面说的,似乎是m和c又要同时生产。
m和c都是一个结构体的数据 代表了这个结构的两个属性 对于生产这个结构体来说只要C消费完就可以开始 M是否消费完都不用考虑 但是M是必须要给A消费的不消费的就是程序的缺陷不能实现 本来的功能 还有补充一点 A也是要消费c的A消费的是两个 这样消费C可以加速 也就加速了 结构体的生产。 [/quote] 无语啊 我问的是 ‘m、c的生产有关系吗’ 你回答‘属于一个结构体啊 ’ 属于一个结构体是你自己定义的啊 必要时可以改嘛
JohnYale 2013-06-07
  • 打赏
  • 举报
回复
遇到郭靖式的学生 老师只好石化
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 17 楼 lhylhy 的回复:
[quote=引用 16 楼 bbc9527 的回复:] [quote=引用 15 楼 lhylhy 的回复:] 两个线程功能分配不合理,需要改进设计。
这个是需求 而且怎么分配不合理了? 本来就是两个线程并发执行提高效率的 怎么不合理了 如果有一个适合的存储结构就可以解决这个问题了 可是我真不知道怎么写 [/quote] 两个线程如此分配功能只能说是设计,怎么能说是需求?你连需求和设计都分不清当然不会写程序。[/quote]还有你既然可以写就重新写一个吧。两个线程如此分配功能既可以是设计也可以是需求,对于设计的人来说是设计,对于执行的人来说是需求,角度不同自然说法不同。
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 17 楼 lhylhy 的回复:
[quote=引用 16 楼 bbc9527 的回复:] [quote=引用 15 楼 lhylhy 的回复:] 两个线程功能分配不合理,需要改进设计。
这个是需求 而且怎么分配不合理了? 本来就是两个线程并发执行提高效率的 怎么不合理了 如果有一个适合的存储结构就可以解决这个问题了 可是我真不知道怎么写 [/quote] 两个线程如此分配功能只能说是设计,怎么能说是需求?你连需求和设计都分不清当然不会写程序。[/quote] 那你设计更强的,需求里面包括了性能需求和功能需求,我这个既满足了功能也满足了性能,而且我的这里的需求不是软件的需求是客户指定的要求的那种需求歧义罢了,客户要求我这么个流程这么个多线程难道不可以说需求么?这个就是要求多线程,你要怎么分配才合理? 你要么好好修改 我那程序 如果改出更好的我给客户看,自然他就可以接受我的改变了
lhy 2013-06-07
  • 打赏
  • 举报
回复
引用 16 楼 bbc9527 的回复:
[quote=引用 15 楼 lhylhy 的回复:] 两个线程功能分配不合理,需要改进设计。
这个是需求 而且怎么分配不合理了? 本来就是两个线程并发执行提高效率的 怎么不合理了 如果有一个适合的存储结构就可以解决这个问题了 可是我真不知道怎么写 [/quote] 两个线程如此分配功能只能说是设计,怎么能说是需求?你连需求和设计都分不清当然不会写程序。
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 15 楼 lhylhy 的回复:
两个线程功能分配不合理,需要改进设计。
这个是需求 而且怎么分配不合理了? 本来就是两个线程并发执行提高效率的 怎么不合理了 如果有一个适合的存储结构就可以解决这个问题了 可是我真不知道怎么写
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 30 楼 JohnYale 的回复:
[quote=引用 26 楼 lhylhy 的回复:] 你口口声声满足了功能和性能,那你来这问什么? 你到现在没有说你要做什么,别人怎么可能给你解答。 你几乎冷言拒绝了所有合理的建议,却有来这里问问题,难不成大家都欠你钱。
随他去吧。问题没说清楚,却怪别人没看明白。线程的使用本来是我比较专长的部分,朋友一篇关于线程论文的示例程序就是我写的。算了,随他去吧
引用 27 楼 u010946993 的回复:
初学者,看这个觉得好绕,抓紧学习去
建议你去看一下《Microsoft Win32 程序员参考大全》第二卷,比这明白的多[/quote] 听说你比较擅长 有时间研究我这个问题 顺便发个论文什么的,貌似并行计算是以后的热点 还有 你觉得看不明白 但是我问的好多人还是明白了 顺便给了我很多思路 所以我感觉 我说的还是可以让人理解的吧,至于你为什么不理解,我想我也不知道。
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
问题已经解决了 你专长的部分都看不明白我的意思,我都觉得好笑。 主要是思路 ,你连思路都没有 我在一个群里 有一个朋友给了我启发用队列操作实现这个同步,他的代码简单明了虽然是c++的,但是我知道了思路,今天我找了很多的代码 都弄的复杂无比,到最后我看的烦了,就用了下最简单的list类,然后通过list类存储数据 还有对list类的数据进行修改 删除添加,完美实现我的要求, 主要是思路 你说了那么多不找边际的话,一点关键都没点到。还好意思说自己擅长。我就不说其他了,问题已经解决了,我晚上可以安心睡觉了。
lhy 2013-06-07
  • 打赏
  • 举报
回复
两个线程功能分配不合理,需要改进设计。
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
引用 13 楼 JohnYale 的回复:
线程同步不难,但很麻烦。 同步对象除了临界区之外,还有互斥、事件、信号量等,按照不同的要求合理选择才行。 你的问题我简化了一下,不知与你原意相符吗 m给A消费,消费完了再生产 c给B消费,消费完了再生产 问一下 m、c的生产有关系吗?似乎没关系---属于一个结构体啊 怎么没有关系 你看过代码么 但你在后面说的,似乎是m和c又要同时生产。
m和c都是一个结构体的数据 代表了这个结构的两个属性 对于生产这个结构体来说只要C消费完就可以开始 M是否消费完都不用考虑 但是M是必须要给A消费的不消费的就是程序的缺陷不能实现 本来的功能 还有补充一点 A也是要消费c的A消费的是两个 这样消费C可以加速 也就加速了 结构体的生产。
JohnYale 2013-06-07
  • 打赏
  • 举报
回复
线程同步不难,但很麻烦。 同步对象除了临界区之外,还有互斥、事件、信号量等,按照不同的要求合理选择才行。 你的问题我简化了一下,不知与你原意相符吗 m给A消费,消费完了再生产 c给B消费,消费完了再生产 问一下 m、c的生产有关系吗?似乎没关系 但你在后面说的,似乎是m和c又要同时生产。
山东蓝鸟贵薪 2013-06-07
  • 打赏
  • 举报
回复
我也不会 简单的线程学习的 http://bbs.csdn.net/topics/390445877
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
你写的太绕,大概看了一下,就是两个线程,B相当于缓冲区,A从B中获取。 1.看你的代码最主要一点是在线程中直接去操作了窗体,这点应该避免。---这个是为了调试输出的需要,是分开的两个窗体关系不大吧。没有输出怎么监视?即使用日志也是要操作文本的,这个冲突我尽量用sleep缓解了 2.没有必要在A线程中创建B,两件事就分的清清楚楚,不要混在一起,直接在主程序中创建A和B。---为什么没有必要?本来就是想提高效率 让 shiwuc.c shiwuc.w 不必同时消耗完 才开始生产 让 shiwuc.c消耗完就开始生产 ,同时存储 shiwuc.w让A消耗 ,这样生产的时间减少了 可以提高效率 你应该理解我采用多线程是为了加速生产。单线程的话 是无法做到的,不相信你可以尝试。 3.看你的代码应该是两个线程的共用资源是一个结构体的两个数字,这样的操作要两个线程吗?----一个结构体的两个数字代表的是一个类的两种不同资源,为什么不可以两线程?两种资源消耗和生产用两线程协调难道不对么? 4.你好象是在检查一个数据,如果为0就让另一个线程B去生成一个随机数,就是你说的生产。-------这是一个模拟器 。为0的意义是该类的某个资源被线程消耗完毕需要生产 生成一个随机就是为了简单说明的需要,用纯固定数字 太不容易看出效果,这样随机+固定是可以增强效果的 然后A线程在对这个数字进行递减,就是你说的消费。这样的业务根本没有必要搞两个线程。用下面的逻辑实现:-------------你没有理解多线程的用途,提高效率 并发执行就是多线程的初衷。 procedure 消费 begin EnterCriticalSection(My); try if 检查是否有值可以消息,如果没有 给结构体赋值,进行生产 给结构体减持消费; finally LeaveCriticalSection(My); //离开临界区 end; end; -----------------这样会产生等待 浪费了时间------------------一个消费要等另外一个消费 多个线程只进行消费就OK procedure Tthread.Execute; begin while true do procedure 消费 end; end; 只处理消费会导致不协调 无法管理控制生产
bbc9527 2013-06-07
  • 打赏
  • 举报
回复
楼主到底是要解决线程同步问题还是解决程序问题?----程序设计的问题,就是要实现这个程序能够协调两个线程操作。 说出你的需求 大家给出思路多好 。---------------------------------------------------我的需求说的很明白啊。shiwuc.c=0就是 B线程消耗 shiwuc.c消耗完之后即可开始shiwuc的生产 但是因为shiwuc.w没有消耗完,所以要保存这个shiwuc.w的数据让A消耗,然后shiwuc.c被B线程消耗。这样B不用等待A消耗完,明白我的意思么?
JohnYale 2013-06-07
  • 打赏
  • 举报
回复
引用 26 楼 lhylhy 的回复:
你口口声声满足了功能和性能,那你来这问什么? 你到现在没有说你要做什么,别人怎么可能给你解答。 你几乎冷言拒绝了所有合理的建议,却有来这里问问题,难不成大家都欠你钱。
随他去吧。问题没说清楚,却怪别人没看明白。线程的使用本来是我比较专长的部分,朋友一篇关于线程论文的示例程序就是我写的。算了,随他去吧
引用 27 楼 u010946993 的回复:
初学者,看这个觉得好绕,抓紧学习去
建议你去看一下《Microsoft Win32 程序员参考大全》第二卷,比这明白的多
加载更多回复(14)

16,748

社区成员

发帖
与我相关
我的任务
社区描述
Delphi 语言基础/算法/系统设计
社区管理员
  • 语言基础/算法/系统设计社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

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