有两个用Delphi编写的服务。一个服务在服务器上运行,另一个服务在客户端上运行。这两个服务通信以在客户端和服务器之间交换数据。在这种情况下,服务器服务要求客户端发送数据,但是在一天左右之后,服务器上分配的内存超过了它的物理大小。经过一些研究,我发现下面这两个函数出了问题。
以下代码中是否有内存泄漏?
服务器服务:
import java.io.*;
import java.net.*;
class TCPClient
{
public static void main(String argv[]) throws IOException
{
String sentence;
String modifiedSentence;
Socket clientSocket = new Socket("*localhost*", *portnum*); // new Socket("192.168.1.100", 80);
System.out.println("Enter your ASCII code here");
BufferedReader inFromUser = new BufferedReader( new InputStreamReader(System.in));
sentence = inFromUser.readLine();
// System.out.println(sentence);
while(!(sentence.isEmpty()))
{
DataOutputStream outToServer = new DataOutputStream(clientSocket.getOutputStream());
outToServer.writeBytes(sentence);
BufferedReader inFromServer = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
modifiedSentence = inFromServer.readLine();
while(!(modifiedSentence.isEmpty()))
{
System.out.println("FROM SERVER: " + modifiedSentence);
break;
}
System.out.println("Enter your ASCII code here");
inFromUser = new BufferedReader( new InputStreamReader(System.in));
sentence = inFromUser.readLine();
}
System.out.println("socket connection going to be close");
clientSocket.close();
}
}
客户服务:
function TServerMethods.LogInMngr_GetAllUsers(): TList<TLogInClass>;
Var
C: TDBXCommand;
Begin
C := CreateCommand('LogInMngr_GetAllUsers');
try
C.ExecuteUpdate;
Result := GetValue<TList<TLogInClass>>(C.Parameters[RP]);
finally
C.Free;
end;
end;
数据位于类function TLogInMngrClass.GetAllUsers(status: TLogInStatus = lisUnknown): TList<TLogInClass>;
var
LogIn: TLogInItem;
LogInTemp: TLogInClass;
UsedProg: TUsedItem;
begin
Result := TList<TLogInClass>.Create;
for LogIn in LogInList do
if (status = lisUnknown) or (LogIn.Status = Integer(status)) then
for UsedProg in LogIn.UsedProgList do
begin
LogInTemp:=TLogInClass.Create(LogIn.ClientID, LogIn.ComputerName, LogIn.UserName, '', '');
LogInTemp.LogInTime := DateTimeToFileTime(UsedProg.AccessTime);
LogInTemp.Status := LogIn.Status;
LogInTemp.ProgName := UsedProg.ItemName;
LogInTemp.ProgVersion := UsedProg.ItemInfo;
Result.Add(LogInTemp);
end;
end;
中,结果将使用TLogInClass
作为类TLogInClass
的通用列表返回。
答案 0 :(得分:0)
答案 1 :(得分:0)
正如其他人所提到的那样,你没有表明&#34;结果&#34;客户端的功能是内存管理的。
我怀疑GetAllUsers作为客户端被多次调用,这反过来会激活Create多次,这会增加内存消耗。
除此之外,我总是发现难以管理按功能返回的对象。很难确定&#34;结果&#34;的结果和时间。应该被释放,是否被释放。
目前,服务器端功能并未意识到&#34;谁负责管理结果。
我会将该函数重写为具有如下参数的过程:
procedure TServerMethods.LogInMngr_GetAllUsers (var userList: TObjectList<TLogInClass>);
begin
if not assigned(userList) then
raise Exception.Create('userList not instantiated');
...
end;
然后调用此过程:
var
tmpUsers: TObjectList<TLogInClass>;
begin
tmpUsers:=TObjectList<TLogInClass>.Create;
try
ServerMethods.LogInMngr_GetAllUsers(tmpUsers); <--- or whatever you call the ServerMethods class
.....
finaly
tmpUsers.Free;
end;
端;
通过这种方式,您可以清楚地管理列表的生命周期。
也许我不遵循你的设计或遗漏一些内容,但我认为你明白了使用程序而不是函数来管理对象。