2017-04-14 82 views
1

我目前正在嘗試編寫一個小型多人遊戲的網絡部分,而且我面臨的問題是存儲我的TCP套接字,這些套接字在SFML中是不可複製的(我是一個初學者C++)。使用SFML處理多個客戶端套接字

我有三類:ServerClientClientManager(用於存儲連接的客戶端所有信息的服務器端類),它負責存儲所有的客戶,並給他們的ID等

ClientManager.h

class ClientManager { 
    public: 
     ClientManager(); 
     std::map<int, Net::Client*> getClients(); 
     int attribID(); 
     void addClient(Net::Client *client); 
     sf::TcpSocket getClientSocket(int id) throw(std::string); 
     void setClientSocket(int id, sf::TcpSocket); 
    private: 
     std::map<int, Net::Client*> m_clients; 
     std::map<int, sf::TcpSocket> m_clientSockets; 
     std::vector<int> m_ids; 
     int m_lastID; 
}; 

我打算怎麼做最初,當客戶端連接,方法是:

void Net::Server::waitForClient() { 
    while(true) { 
    if(m_listener.accept(m_tcpSocket) != Socket::Done) { 
     cout << "Error happened during client connection. skipping. " << endl; 
     return; 
    } 
    int newID = m_clientManager.attribID(); 
    this->m_clientManager.addClient(new Net::Client(newID, m_tcpSocket, m_tcpSocket.getRemoteAddress())); 
    } 
} 

因此,將一個新的Client添加到ClientManager的列表中,使用它的ID,一個TcpSocket發送信息和他的地址。

但問題是,SFML的TcpSocket類不可複製,這意味着我不能將它複製到像這樣的客戶端。

我可以將它作爲指向原始TcpSocket的指針傳遞,但如果另一個客戶端連接呢?指針指向的數據將會改變,程序將會出錯。我不知道這種行爲是否與智能指針相同,但我認爲是這樣(但我根本不掌握它們)。

將它們存儲在std::mapstd::vector中會導致相同的問題,因爲它們都複製對象。將它們存儲爲原始TcpSocket中的指針(在映射中)將導致與以前相同的問題,因爲套接字也會改變,並且指針將指向同一個對象。

如何存儲我的套接字而無需使用引用,指針或複製我的對象?

任何幫助,將不勝感激:)

+0

當我回家時,我將不得不更多地瞭解這一點,但我相信你可以將套接字的地址傳遞給clientManager,然後從套接字獲取IP和端口信息並將其存儲。 – Eddge

+0

您可以使用動態內存,使用std :: unique_ptr或shared_ptr,並將指針存儲在vector/map中(這將要求您爲每個連接分配內存)。 – Eddge

+0

嘿,謝謝你的回答!它確實需要爲每個新連接的客戶端分配內存(或者我們只會遇到指針的情況)。通過分配內存,你的意思是:在while循環開始時創建一個'shared_ptr'指針,用'new'分配內存,然後有一個'std :: map >'(或任何其他方式與另一個'shared_ptr')將它們存儲在'ClientManager'中? – cocosushi

回答

1

這將是一個真正的痛苦,而不指針做。我個人使用智能指針來管理套接字本身(std::vector<std::unique_ptr<sf::TcpSocket>>或類似),以及`sf :: SocketSelector'來管理實際的通信

+0

這就是我所做的,正如我在回答Eddge時的建議,除了我使用了一個'std :: map'(因爲我需要一個ID)和'std :: shared_ptr'(我不知道它是否適合我的用例,因爲我沒有很好地掌握智能指針,但至少有作品)。我也結束了使用'sf :: SocketSelector' :) – cocosushi

+0

我建議在可能的地方使用unique_ptr over shared_ptr(大量的互聯網參數在這方面浮動,我不會承擔你......),但我懷疑它會造成你的任何問題。很高興它的工作:) –

+0

我會稍後看一看(大)看,這是我想知道更多關於主題的一部分:) – cocosushi