我买了一个四口的短信猫,想实现通过四个串口群发短信,有他们的控件,对于一个串口,调用发送的事件就可发送,大概用时7秒。
我想实现四个串口同时发送,大家帮忙想想用什么方法?单串口发送程序:
    begin
      if SMS.SendMsg(txtMobileNo.Text,txtMsg.Text ,true,false) = 0 then
        ShowMessage('发送成功!')
      else
        ShowMessage('发送失败!');
    end我想了想觉得挺难的,请高手点拨!

解决方案 »

  1.   

    请问你的 GSM morden 是什么牌子??? 多少钱??? 在哪里买 ???????
      

  2.   

    有个关键问题,使用多线程可行么
    关键问题先要测试下对方的给你的控件能不能支持啊以及那个morden支持否
    测试方法,
    你写程序写一个串口
    那么你同时开启4个程序,快速按下发送(4个程序)估计你能在4秒内搞定
    如果这样可以,那么你就可以在多线程中实现了另外如果他们给你的是控件,你可以在一个程序里面同时控制4个这个ocx
      

  3.   

    每个用户连接一个线程是什么意思,你的串口还能实现多用户么,我想不可以吧,要不然就不用4个口短信moden了。如果每个每个用户就是每个串口的话,那就简单了,也就是往一个串口里面写数据,不会影响你继续在往另外一个串口里面写啊。
    你用的是什么短信moden这么慢,要7秒一条短信,太慢了吧,我有点明白一点了,7秒钟是等待移动的
    回复成功的信息了。那么可能就慢了点了。另外一个好点的办法,就是搞一个发送短信息的列表,一条一条发送,成功的打成功标记,不成功的打失败标记不是更好点么。
      

  4.   

    这确实是个好办法,可是我不会呀,短信列表怎么弄?
    我说的每个用户一个线程,是指我的软件是一个网络软件,很多客户端,一个服务器端。用的是idtcpserver控件,他是自动为每个连接的用户创建一个线程的。用户发送短信请求到服务器端,服务器就通过这四个串口发送短信。
    我写了一段程序,基本可以充分利用这几个串口同时发送,但仍问题多多:procedure TForm1.Timer1Timer(Sender: TObject);//现在假设只有两个串口
    var
      phone : string;//单个手机号
    begin
      if Num>CheckNum then begin  //发送完毕,退出timer,这里有问题,关闭程序时会没反应。
      timer1.Enabled := false;
      //application.ProcessMessages;
      showmessage('发送短信完成,您共请求发送'+ inttostr(checknum) + '条短信,公成功发送'+inttostr(sucessnum)+'条');
      end;  if sms1.State=0 then     //查看串口(设备)一的状态是否空闲,是则发送,
      begin
      phone:=copy(PhoneStr,Num*12+1,11);//分离出单个手机号
      inc(Num);                //num用来记录要发送第几个手机号了
      send1(phone,'深刻搭街坊集散地法律');//调用串口一发送函数。
      end
      else if sms2.State=0 then
      begin
      phone:=copy(PhoneStr,Num*12+1,11);//分离出单个手机号
      inc(Num);
      send2(phone,'秋高气爽,落叶知秋');
      end
      //else exit;
    end;procedure TForm1.Button1Click(Sender: TObject);
    begin
      sucessnum := 0; //计算发送成功的条数
      PhoneStr :='13001800122,13231196504,13832137560,';//要群发的手机号
      CheckNum := Length(PhoneStr) div 11;              //要发送多少个手机号
      num := 0;                                         //记录要发送第几个手机号
      timer1.Enabled := true;
    end;问题:
    1、为什么退出timer循环后,关闭程序会没有反应?怎么解决?
    2、如果两个用户同时发送请求,是不是就乱了?用线程同步的原理能不能控制一个用户的请求完毕之后再执行另外一个用户的请求?大侠帮忙!!!
      

  5.   

    对于这样的问题应该是采用多线程,本人同意赞成YANGYUGW(小杨) 用一个发送短信息的列表,
    在界面上是主线程来取数据,然后分别把发送任务,发送消息到各线程处理发送短信息的任务,
    线程中在处理成功的时候把这个发送短信息的列表的标志做为完成标志,否则为失败标志。
    这样 应该可以达到要求。
      

  6.   

    如果每发一条都要7条,这跟单口的有什么区别?检查一下短信猫,有没有异步发送或后台发送的说法。(SendSMS的第3、4个参数都是干什么的?)
      

  7.   

    3、4个参数:
    3:Chinese      布尔型    是否为中文短消息 (True=中文  False=西文)
    4:NeedReport   布尔型    是否需状态报告 (True=需要  False=不需要)
    他这个控件是针对单口设备的,至于多口,要用多个控件,之间的协调要自己写程序,也就是我现在需要的程序。
      

  8.   

    因为SendSMS没有后台执行的能力,所以必须要用线程处理。
    1.创建4个线程,分别打开4个串口;
    2.线程从主程序取要发送的记录
        使用信号量进行线程间同步,即:主程序每向队列中加一条,将信号量加1;发送进程每从队列中取走一条,将信号量减1。如果队列为空,线程将挂起(可以理解为等待在队列上,不占用系统资源)
      

  9.   

    我同意上面朋友说的,你需要看下多线程的书籍
    也就是说具体线程怎么实现的,可以参考书籍(其实多线程很简单)
    简单的就是,定义一个函数,然后建立线程运行这个函数,就是这样的,不过delphi做的有点复杂
    因为最近看C#中的线程的实现,比较简单而且明了些,但在怎么说,delphi的多线程这部分也不是特别难了,delphi有个例子好像是排序的那个,用了多线程,关于线程我就不多说了,因为有很多书籍介绍
    你我上面的话就是要给你树立个信心,去看看,然后操作下,就应该可以了根据你的说法,网络使用的是idtcpserver控件,那么网络部分多线程控制client部分你不用管理的
    因为idtcpserver可以自己管理。问题来的我想知道  phone:=copy(PhoneStr,Num*12+1,11);//分离出单个手机号
      inc(Num);                //num用来记录要发送第几个手机号了
      send1(phone,'深刻搭街坊集散地法律');//调用串口一发送函数。这一段代码最后一句话从执行开始到跳转道下一指令用了多久
    如果这一句话是阻塞的方式的话那就需要多线程,否则不用使用
    我的感觉不像阻塞方式,因为控件有一个状态让你监测么,说明
    你可以同时,顺序在同一时间操作4个串口,应该对吧我想的想法,你是不是怕客户端发送n条短信,那么你的4个串口不够发送对吧如果客户端始终发送给你的短信,一直都让你的4个串口无法忙过来的话 ,那么一定
    会溢出。这是无法解决的。但是如果同一时刻发送1000条短信给你,但是会给你一段时间
    让你有机会处理这1000条的话,那么就有解决方法了你可以通过list来存储客户端发给你的要求你发送的短信,来一条加一条
    然后同时在timer中发送了,list就是缓冲,我出学的时候还曾经使用过数据库来存储的
    其实原理一样的。你说的关闭程序没有反应,是因为你调用了控件没有处理完的部分,所以可能会出现这样的问题要知道最关键的问题我觉得在于send那条的执行时间,如果很快执行,我觉得不需要使用多线程
    但是list一定是需要的,因为你不能保证客户的短信你马上就可以发送出去。
      

  10.   

    lyre(大头鬼) ( ) :能给点相关的程序提示吗?
    我真的是很无奈了,都做好几天了。
      

  11.   

    to  YANGYUGW(小杨) :
    1、线程的资料我看过一些,有些浅显的了解。
    2、咱先不说idtcpserver的那些线程,就当作单个用户要发送短信。
    3、我这段程序就是想用timer定时去查询每个设备的状态,如果空闲就给他一个手机号去发送。timer的循环时间是0.5s,
    send1(phone,'深刻搭街坊集散地法律');//调用串口一发送函数。这一行大概要执行4s
    4、简单几个手机号测试算成功了,但多了估计毛病就多了,而且现在不知道怎么发送完之后自动推出timer的循环。
    5、我的这个做法,如果多用户操作时肯定就出错了,所以我现在也觉得还得用线程。希望能给深一点的提示。缓冲也是要的,列表的这个方法很好,比我用变量来控制好多了。对了,可以把所有用户发过来的手机号都放在list里面,然后交给串口发送程序去发,这样就不会产生矛盾了吧
    6、谢谢大家给我的提示,因为着急,所以请大家帮帮忙,分不够还可以另开贴。
      

  12.   

    以下是我试写的一些代码,希望能帮到你,没有编译,可能会有语法错误。
    unit Usendthreadinterfaceuses Classes,SysUtils,Controls,StdCtrls;
    type
    sendthread=class(TThread)private
    sendph:string;
    sendcommnum:integer;protected
    procedure Execute;override;
    procedure work;public
    constructor create(ph:string;comnum:integer);
    end;implementationconstructor sendthread.create(ph:string;comnum:integer);
    begin
    inherited create(true);
    sendph:=ph;
    sendcommnum:=comnum;
    //在实体工作中使用他们进行发送
    freeonterminate:=true;
    resume;
    end;procedure sendthread.work;
    begin
    //工作实体
    endend;procedure sendthread.Execute;
    begin
      work;
    end;
    end.
    //以下为调用部分procedure OnTerminatesend(sender:TObject);//线程结束事件
    var ThreadCount:byte;procedure myProgram.OnTerminatesend(sender:TObject);
    begin
    dec(ThreadCount);
    end;
    procedure myprogram.sendclick(sender:Tobject);
    begin
    //调用方法,在这之前你要查询哪个串口可用,如果没有一个可以用那么你就不用开始线程了
    //在list取出一个,切忌一定要将取出的那个item删除掉。
    //以及判断线程的运行数量,根据你的情况估计不会超过4个
    with sendthread.create(ph,1) do
    nterminate:=OnTerminatesend;
    inc(ThreadCount);
    end;
      

  13.   

    //调用方法,在这之前你要查询哪个串口可用,如果没有一个可以用那么你就不用开始线程了问:查出哪个串口可用,是要把这个串口号传入发送函数吗?发送函数就写一个吗?这几个线程里执行的函数或过程就是一个吗?
    //在list取出一个,切忌一定要将取出的那个item删除掉。问:list是什么?listbox吗?把它设成不可见的?每个用户发送的手机号就往里面添加吗?但每个用户要发送的短信内容是不一样的,这个怎么控制?//以及判断线程的运行数量,根据你的情况估计不会超过4个
    这4个线程是动态创建的吗?还是预先创建好,发现某个串口可用后就开始?
      

  14.   

    >>问:list是什么?listbox吗?
     TStringList>>这4个线程是动态创建的吗?还是预先创建好,发现某个串口可用后就开始?
    动态创建線程的, 你要看看書, 寫一兩個簡單的例子測試下, 再寫應該就沒問題了
      

  15.   

    constructor sendthread.create(ph:string;comnum:integer);
    begin
    inherited create(true);
    sendph:=ph;
    sendcommnum:=comnum;
    //在实体工作中使用他们进行发送
    freeonterminate:=true;
    resume;
    end;这两个参数是什么意思?怎么用?线程是动态创建的,也就是说根据参数的不同创建了不同的而创建了不同的线程,是吗?那怎么传参数到procedure sendthread.Execute;这个过程里面的。
      

  16.   

    好像可以了,线程这里,按YANGYUGW(小杨)说的做的。非常感谢大家。