1.首先,你的信号量,定义有问题。 信号量应该是一个全局变量,或你的多个线程的局部变量,而不应该是单个线程的私有变量,这样多个线程才可以通过它来同步,否则同步是不起作用的。
type
  TMyThread = class(TThread)
  private
    FParentHandle: THandle;
    FSemaphore: THandle;

解决方案 »

  1.   

    多谢airhorse(编程至尊宝)又来捧我的场。
     
    小子对这多线程总是有点糊涂,所以根据那VCL的一个类写了个Demo,它也是这么定义的。
    那个类好像是启用线程来发送数据。如果信号量要全局变量,那把它定义到TForm1中,再传到线程也可。
    不如你跟我讲讲信号在线程中的作用吧。
    请继续。
      

  2.   

       木兄,又要见笑。我们还是探讨为先。只是我以前作过几个这样的程序,手头没用工具(delphi,网吧),有讲错还望,一一指正。
        
        多线程同步,通常用的最多的是,多个功能相同的工作线程之间的同步。多个功能相同的工作线程在一起,通常又叫线程池.他们要完成特定的随机产生的多个任务。单个的任务通常映射为一个消息,多个任务映射的多个消息通常称为消息池。
      

  3.   

    非常受教
    我说觉得在那个线程中用不用Semaphore是一样的。原来是为了多线程中同步访问消息资源而弄的。
    那个信号好像只有CreateSemaphore是只允许一个线程来访问,如果是多个需要的话,那在线程中建立就没什么意义了。不错。
    每个线程中必须要ReleaseSemaphore将这信号置为signaled,表示已经有线程使用了这个,那怎么当线程完成后,再把它置为noSignaled.用什么函数。
    这信号的API好像只有CreateSemaphore,OpenSemaphore,ReleaseSemaphore,
    是用OpenSemaphore吧,打开一个存在的Semaphore对象。它会不会将信号置noSignled,
    还有如果ReleaseSemaphore不成功,它是等待,还是怎么样
      

  4.   

    不错,看了下help,ReleaseSemaphore果然是将阻塞进程好,同步明白了。
    接下来是MsgWaitForMultipleObject返回值。
    那个Wait_Object_0值它什么时候才会返回。
    还有Time_Out.各位虾们,不是我不想给分,只是俺是初级用户,只能给这些分。
      

  5.   

       再CreateSemaphore里有一个参数,设置可将信号量设为自动,但一个线程用waitforsinglObject(...),取得一个消息的时候,信号量自动减一。   OpenSemaphore,是取得一个特定的信号量(用名字来区别)的句柄,通常是信号量的消费者用来打开信号量。不会singaled信号量。
       ReleaseSemaphore,是信号量加一。不成功会返回错误码的吧。
      

  6.   

    那个同步还是不行呢。
    我看了下help,它说用ReleaseSemaphore将信号占用后,用信号句柄用Wait function调用返回后将会置为noSignled,但是我没有用它的句柄作为参数进行调用啊。所以Wait function不会置noSignled,怪了,那它该什么置了,用什么来置了?
      

  7.   

    好,这会这个WaitForSingleObject真是明白明白了,哈哈。
    FMyThread := Create ===> Execute(ReleaseSemaphore, MsgWaitForSingleObject) ==>
      线程结束后,WaitForSingleObject将置信号为noSigned(可以同时启动另个进程,不过由Semaphore控制着)
    呵呵,多谢宝兄
    继续  MsgWaitForMultipleObject
      

  8.   

     
        干哈,干哈呀?
          收分呗  
    顺便,up提高收视率!
    顺便,up提高收视率!
    顺便,up提高收视率!   
      

  9.   

         木兄:
        发错了,不好意思。    没有工具(delphi,msdn,网吧),下次再说吧?
      

  10.   

    //线程中除了Wait_Object_0 + 1会执行外,其它的都case 不了。//请各位高手说一下会触发Wait_Object_0, Wait_TimeOut的情况procedure TMyThread.Execute;
    var
      Msg: TMsg;
    begin
      ReleaseSemaphore(FSemaphore, 1, nil);
      while not Terminated  do
        case MsgWaitForMultipleObjects(1, Msg, False, ThreadTimeOut, QS_ALLINPUT) of
          WAIT_OBJECT_0:  //这个Case什么时候触发啊。
              PostMessage(FParentHandle, WM_MyMessage, Msg.wParam, Integer(Pointer(PChar('I don''t not mean'))));
          //如果有消息,将把从消息队列中全部取出并删除,看是否自己定义的消息,不然交由VCL自带的处理方式处理。     
          WAIT_OBJECT_0 + 1:                                //取出并删除
            while PeekMessage(Msg, 0, WM_USER, WM_MyMessage, PM_REMOVE) do
              if Msg.hwnd = 0 then   
                if Msg.message = WM_MyMessage then
                   PostMessage(FParentHandle, WM_MyMessage, Msg.wParam, Msg.lParam)
                else DispatchMessage(Msg)
              else DispatchMessage(Msg);
          WAIT_TIMEOUT:  //为什么不触发TimeOut,在哪设,是不是说上面的WaitFor执行的期间,如果没有消息,它是挂起的啊
          begin
            Terminate;
            PostMessage(FParentHandle, WM_MyMessage, Msg.wParam, Integer(Pointer(PChar('Time Out'))));
          end;
        end;
    end;
      

  11.   

    case MsgWaitForMultipleObjects(1, Msg, False, ThreadTimeOut, QS_ALLINPUT) of  //有问题DWORD MsgWaitForMultipleObjects(
      DWORD nCount,          // number of handles in the handle array
      LPHANDLE pHandles,     // pointer to the object-handle array
      BOOL fWaitAll,         // wait for all or wait for one
      DWORD dwMilliseconds,  // time-out interval in milliseconds
      DWORD dwWakeMask       // type of input events to wait for
    ); pHandles:通常是指向信号量,不知道木兄,为何要指向,一个消息。//线程中除了Wait_Object_0 + 1会执行外,其它的都case 不了。
    也就是这个问题。
     多个工作线程,为了协调完成多个任务。必将同步有序的访问他们的消息池。
    这个消息池,一般都是自定义的消息队列。用wondows消息干扰太多。
    Waitfor函数一般也用WaitForMultipleObjects,WaitForSingleObject
      

  12.   

    哈哈,不好意思,我搞了那久都没看到这个错误,不经你提醒,那线程永远也不会执行到Wait_Object_0那里。过而改之。type
      TMyThread = class(TThread)
      private
        FParentHandle: THandle;
        FSemaphore: THandle;
        FEvent: TSimpleEvent; //增加一个控制事件对象。
      protected
        procedure Execute; override;
      public                                //由调用线程传来。
        constructor Create(ParentHandle: THandle; Event: TSimpleEvent);
        destructor Destroy; override;
        property Semaphore: THandle read FSemaphore;
      end;procedure TMyThread.Execute;
    var
      Msg: TMsg;
      Event: THandle;
    begin
      ...
      Event := FEvent.Handle;
      ...
         MsgWaitForMutipleObjects(1, Event, False, ThreadTimeOut, QS_ALLINPUT) of
      ...
    end;
    //OK
    FEvent是由主调用线程创建的一个Mutux事件,另外还有一个线程也是调用了这个Mutex事件句柄。它可能会触发这个Mutext事件。那么在这个线程中的MsgWaitForMutipleObjects就会返回Wait_Object_0这个值了。终于明白了。
    如果大家有兴趣,可以看TSocketConnection,还有它关联的TSocketTransport,TTransportThread类,它们是相互工作的。
    这个Demo就是根据它写的,不过那个MsgWaitForMutipleObjects写的.....哈哈。
    所以,在此非常多谢  airhorse(编程至尊宝) 
    114分等会送上。让大家看看。