这样会死锁,请解释原因。并使其不会死锁。(已经解决问题, 散分) (300分)

  • 主题发起人 主题发起人 wlmmlw
  • 开始时间 开始时间
呵,误会了。
我确实是想知道为什么会锁。
你的方法很好。如果按你说的,是不是每一个线程同步的时候我们都要while一下呢?
我觉得那样很是别扭,不知你是否会有这种感觉?
 
确实,但那是你自己找的。
 
哈。
好苦啊,还得喝下去。
还得去查。
 
你不帮我了?
 
心情被你搞的不爽,不想帮了。
 
哦,今晚睡个好觉,明天心情就会好起来的。
 
你居然一个星期都没有搞定,可怜。对于我3分钟就搞定,因为我已经遇到过无数这样的问题了,已经不是问题了。
明天我的心情会好起来,因为我会忘掉这个问题。
 
没有了你的乱搞,我的心情当然会好起来
 
别打击我啊。
你找到的只是条小路。嘿嘿[:D]
 
我就知道你根本没有把我的解答放在眼里。
我也不说什么了,你自己找你的阳关大道吧。
顺便说一句,阳关大道有的是,我这都还有好几条。我想你一定能找到,只不过是时间问题而已。我告诉你的那条道,既不是阳关大道,也不是小路,是把你引出死胡同的路。
 
老兄,死在哪里了?在TOpenThread.Execute中那行代码执行不下去了?
我这没delphi,你能说明白些吗?
 
哦,好惨啊,不过有你们这些大侠们的帮助,死是死了D[:D]
To Paladin_yf::
如果你没试过,好难说得明白的,因为我也不清楚
 
就这种问题也要一礼拜,我两分钟就找到问题根源了
不过装delphi和学习delphi花了我一个小时!
呵呵!
 
procedure TOpenThread.UpdateCDS;
begin
FCDS.AppendData(FNewData,True);
//在这句死的
Form1.DataSource1.DataSet:=FCDS;
end;
原因是因为执行这句时,对dbgrid1进行更新滚动条操作SetScrollInfo,SetScrollInfo此函数是SendMessage给dbgrid1控件,记住消息是Send的,在未经处理前是不会返回的。而dbgrid1是主线程中的,主线程还处于Button1Click中等待状态,所以它处理不了SetScrollInfo的请求。而SetScrollInfo却在等待主线程的处理,这样就形成了死锁!
你可以简化你的程序试试:如下所示:
procedure TOpenThread.Execute;
begin
form1.edit1.text := 'yf';
//在form1中添加一个edit先
end
这样也会死锁,怎么样,明白根源了吧?
如何修改程序,你自己看着办吧。我建议不要在一个线程中访问另一个线程的控件,而且尽量不要用WaitForSingleObject等待线程句柄,虽然没有错,但是不灵活,必须线程执行完毕后,WaitForSingleObject才会返回。使用事件更好些,在线程执行得差不多了,就SetEvent激活等待线程,可以随时激活等待线程,比较灵活
我好穷啊,分可不可以全给我呀?
 
delphi是挺不错,但是封装得太多,有些东西就得深入研究了
To wlmmlw:
兄台执着精神可佳,不过没有深入到底。
To SS2000:
SS2000兄也不要生气了,大家互相交流嘛^_^
 
To Paladin_yf::
把它修改成下面这样,你说它还死不死? 解释一下.[:D]
procedure TOpenThread.Execute;
var
OwnerData: OleVariant;
RecsOut: Integer;
Params:OleVariant;
Appserver:IAppserver;
begin
OleCheck(CoInitialize(nil));
try
OleCheck(CoGetInterfaceAndReleaseStream(IStream(FStream), IID_IAppServer,
Appserver));
//FNewData :=
//AppServer.AS_GetRecords (FCDS.ProviderName,
//-1,RecsOut,MetaDataOption,'',Params,OwnerData);
//Synchronize(UpdateCDS);
finally
CoUninitialize;
end;
end;
 
改成上面那样,你那死了吗?
我这没有死啊
 
原因我已经讲得很清楚了,在UpdateCDS函数中死的,你把这句注释掉都不会死的
如果还有问题,可能是你的程序没有配置好
 
//这样还死不死?
procedure TOpenThread.Execute;
var
OwnerData: OleVariant;
RecsOut: Integer;
Params:OleVariant;
Appserver:IAppserver;
begin
OleCheck(CoInitialize(nil));
try
OleCheck(CoGetInterfaceAndReleaseStream(IStream(FStream), IID_IAppServer,
Appserver));
FNewData :=
AppServer.AS_GetRecords (FCDS.ProviderName,
-1,RecsOut,MetaDataOption,'',Params,OwnerData);
//Synchronize(UpdateCDS);
finally
CoUninitialize;
end;
end;
 
后退
顶部