delphi中的套接字错误

delphi中的套接字错误,delphi,Delphi,您好,我对以下代码有问题: host := 'localhost'; nickname := 'tester'; canal := '#tester'; code := ''; ClientSocket := TClientSocket.Create(nil); ClientSocket.host := host; ClientSocket.Port := 6667; ClientSocket.Open; if ClientSocket.Socket.Connected = True the

您好,我对以下代码有问题:

host := 'localhost';
nickname := 'tester';
canal := '#tester';
code := '';

ClientSocket := TClientSocket.Create(nil);
ClientSocket.host := host;
ClientSocket.Port := 6667;
ClientSocket.Open;

if ClientSocket.Socket.Connected = True then
begin
  Writeln('Connected!');
  while (1 = 1) do
  begin
    code := ClientSocket.Socket.Read();
    if not(code = '') then
    begin
      Writeln(code);
    end;
  end;
end
else
begin
  Writeln('Error');
end;
问题出在线路上

code: = ClientSocket.Socket.Read();
给我以下的错误

[DCC错误]irc.dpr(35):E2035实际参数不足

尝试将nil作为参数,但我得到了这个新错误

[DCC错误]irc.dpr(35):E2010不兼容类型:“NativeInt”和“Pointer”

我做错了?

Read()
在内部用于触发
OnRead
事件。你不应该直接打电话给它

默认情况下,
TClientSocket.ClientType
属性设置为
ctNonBlocking
。这意味着套接字异步运行,使用内部窗口接收套接字活动的通知。因此,您必须使用
OnConnect
事件来检测成功的连接,使用
OnError
事件来检测失败的连接,使用
OnRead
事件来接收传入数据。您需要一个消息循环,以便可以触发这些事件。例如:

// since you are using a Console app, you can use
// a little hack to assign event handlers...

procedure ClientConnected(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
begin
  Writeln('Connected!');
end;

procedure ClientDisconnected(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
begin
  Writeln('Disconnected!');
  PostQuitMessage(0);
end;

procedure ClientError(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
  Writeln('Socket Error! ', ErrorCode);
  if ErrorEvent = eeConnect then
    PostQuitMessage(0);
end;

procedure ClientRead(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
var
  len: Integer;
  Buf: PByte;
begin
  len := Socket.ReceiveLength;
  if len <= 0 then Exit;
  GetMem(Buf, len);
  try
    len := Socket.ReceiveBuf(Buf^, len);
    if len <= 0 then Exit;
    // use data as needed...
  finally
    FreeMem(Buf);
  end;
end;

var
  ClientSocket: TClientSocket;
  M: TMethod;
  Msg: TMsg;
begin
  try
    ClientSocket := TClientSocket.Create(nil);
    try
      ClientSocket.Host := 'localhost';
      ClientSocket.Port := 6667;

      M.Code := @ClientConnected;
      M.Data := ClientSocket;
      ClientSocket.OnConnect := TSocketNotifyEvent(M);

      M.Code := @ClientDisconnected;
      M.Data := ClientSocket;
      ClientSocket.OnDisconnect := TSocketNotifyEvent(M);

      M.Code := @ClientRead;
      M.Data := ClientSocket;
      ClientSocket.OnRead := TSocketNotifyEvent(M);

      M.Code := @ClientError;
      M.Data := ClientSocket;
      ClientSocket.OnError := TSocketErrorEvent(M);

      ClientSocket.Open;

      while GetMessage(msg, 0, 0, 0) do
      begin
        TranslateMessage(msg);
        DispatchMessage(msg);
      end;
    finally
      ClientSocket.Free;
    end;
  except
    Writeln('Error');
  end;
end.
var
  ClientSocket: TClientSocket;
  Strm: TWinSocketStream;
  len: Integer;
  Buf: array[0..1023] of Byte;
begin
  try
    ClientSocket := TClientSocket.Create(nil);
    try
      ClientSocket.ClientType := ctBlocking;
      ClientSocket.Host := 'localhost';
      ClientSocket.Port := 6667;

      ClientSocket.Open;
      Writeln('Connected!');

      Strm := TWinSocketStream.Create(ClientSocket.Socket, 5000);
      try
        repeat
          len := Strm.Read(Buf[0], SizeOf(Buf));
          if len <= 0 then Break;
          // use data as needed...
         until False;
      finally
        Strm.Free;
      end;
    finally
      ClientSocket.Free;
    end;
  except
    Writeln('Error');
  end;
end.
Read()
在内部用于触发
OnRead
事件。你不应该直接打电话给它

默认情况下,
TClientSocket.ClientType
属性设置为
ctNonBlocking
。这意味着套接字异步运行,使用内部窗口接收套接字活动的通知。因此,您必须使用
OnConnect
事件来检测成功的连接,使用
OnError
事件来检测失败的连接,使用
OnRead
事件来接收传入数据。您需要一个消息循环,以便可以触发这些事件。例如:

// since you are using a Console app, you can use
// a little hack to assign event handlers...

procedure ClientConnected(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
begin
  Writeln('Connected!');
end;

procedure ClientDisconnected(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
begin
  Writeln('Disconnected!');
  PostQuitMessage(0);
end;

procedure ClientError(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
  Writeln('Socket Error! ', ErrorCode);
  if ErrorEvent = eeConnect then
    PostQuitMessage(0);
end;

procedure ClientRead(Self: Pointer; Sender: TObject; Socket: TCustomWinSocket);
var
  len: Integer;
  Buf: PByte;
begin
  len := Socket.ReceiveLength;
  if len <= 0 then Exit;
  GetMem(Buf, len);
  try
    len := Socket.ReceiveBuf(Buf^, len);
    if len <= 0 then Exit;
    // use data as needed...
  finally
    FreeMem(Buf);
  end;
end;

var
  ClientSocket: TClientSocket;
  M: TMethod;
  Msg: TMsg;
begin
  try
    ClientSocket := TClientSocket.Create(nil);
    try
      ClientSocket.Host := 'localhost';
      ClientSocket.Port := 6667;

      M.Code := @ClientConnected;
      M.Data := ClientSocket;
      ClientSocket.OnConnect := TSocketNotifyEvent(M);

      M.Code := @ClientDisconnected;
      M.Data := ClientSocket;
      ClientSocket.OnDisconnect := TSocketNotifyEvent(M);

      M.Code := @ClientRead;
      M.Data := ClientSocket;
      ClientSocket.OnRead := TSocketNotifyEvent(M);

      M.Code := @ClientError;
      M.Data := ClientSocket;
      ClientSocket.OnError := TSocketErrorEvent(M);

      ClientSocket.Open;

      while GetMessage(msg, 0, 0, 0) do
      begin
        TranslateMessage(msg);
        DispatchMessage(msg);
      end;
    finally
      ClientSocket.Free;
    end;
  except
    Writeln('Error');
  end;
end.
var
  ClientSocket: TClientSocket;
  Strm: TWinSocketStream;
  len: Integer;
  Buf: array[0..1023] of Byte;
begin
  try
    ClientSocket := TClientSocket.Create(nil);
    try
      ClientSocket.ClientType := ctBlocking;
      ClientSocket.Host := 'localhost';
      ClientSocket.Port := 6667;

      ClientSocket.Open;
      Writeln('Connected!');

      Strm := TWinSocketStream.Create(ClientSocket.Socket, 5000);
      try
        repeat
          len := Strm.Read(Buf[0], SizeOf(Buf));
          if len <= 0 then Break;
          // use data as needed...
         until False;
      finally
        Strm.Free;
      end;
    finally
      ClientSocket.Free;
    end;
  except
    Writeln('Error');
  end;
end.

您正在调用此方法(),该方法接收名为
Socket
NativeInt
参数。此方法是一个
过程
,没有返回值。显然您调用了错误的方法。我认为ClientSocket.Socket.Read在内部被调用以生成OnRead事件。请看一下如何使用套接字的示例:@DavidHeffernan您在哪里看到参数类型为NativeInt?文档中说,该方法期望TSoCultType。@ DaviHeffer-NeN-CJECK文档,并且您将知道NATEVET的使用是C++,其中我相信NATEVET用于PoTS。Delphi实现不需要TSocket类型的结果。TClientSocket没有读取函数。它有一个OnRead事件。TClientSocket多年来一直被弃用以支持Indy的socket实现,所以我不确定您为什么要使用它;我相信新版本的Delphi实际上已经不再提供它了。您正在调用这个方法(),它接收一个名为
Socket
NativeInt
参数。此方法是一个
过程
,没有返回值。显然您调用了错误的方法。我认为ClientSocket.Socket.Read在内部被调用以生成OnRead事件。请看一下如何使用套接字的示例:@DavidHeffernan您在哪里看到参数类型为NativeInt?文档中说,该方法期望TSoCultType。@ DaviHeffer-NeN-CJECK文档,并且您将知道NATEVET的使用是C++,其中我相信NATEVET用于PoTS。Delphi实现不需要TSocket类型的结果。TClientSocket没有读取函数。它有一个OnRead事件。TClientSocket多年来一直被弃用以支持Indy的socket实现,所以我不确定您为什么要使用它;我相信它实际上不再与更新版本的Delphi一起提供。