面临的困难
如果你想做一个基于UDP包的数据处理问题的话,比较好的办法是使用csv文件来进行数据的保存(csv文件比较简单,方便进行各种处理)。
CSV文件格式简单,一方面它可以直接被excel处理,另一方面它完全由逗号和\0分隔,比较容易转化成Char[]这样的C语言中的变量。
主要功能为:
1.将打算发出UDP包的数据按顺序在csv文件中排好,并由C++开发的程序读取并发出。
2.将接收到的UDP数据按顺序写入一个csv文件之中。
接收得实现方法
CSocket用于数据接收的方式是走如下三步:
1.建立CSocket;
2.调用bind函数建立CSocket与远方客户的联系;
3.数据接收方会自动启用OnReceive函数来响应,在此回调中使用ReceiceFrom函数读取。
所建立的RC文件样式:
所用成员变量一览:
建立CSocket与联系:
void CMFCUDPDlg::OnBnClickedBind()
{
// TODO: 在此添加控件通知处理程序代码
//绑定IP与PORT
CString C_H_IP;
HOST_IP_E.GetWindowText(C_H_IP);
if (m_socket.Create(1234, SOCK_DGRAM, C_H_IP) == 0)
{
CString str;
str.Format(_T("建立监听失败,套接字错误码 : %d"), GetLastError());
STATE_T.SetWindowTextW(str);
MessageBox(str);
}
else
{
CString str;
str.Format(_T("建立监听成功!"));
STATE_T.SetWindowTextW(str);
MessageBox(str);
}
}
这样通过按钮和控件准备好套接字以后,通过监听消息的回调函数OnReceive接收数据。
接收消息:
void CMySocket::OnReceive(int nErrorCode)
{
REF= Receive(buff, 100);
if (REF == SOCKET_ERROR)
{
AfxMessageBox(_T("消息接收失败!"));
}
::PostMessage(AfxGetMainWnd()->GetSafeHwnd(), UDP_RECEIVE, (WPARAM)UDP_RECEIVE, (LPARAM)0);
CSocket::OnReceive(nErrorCode);
}
注意此处的REF与buff都定义在你的socket类中:
class CMySocket : public CSocket
{
public:
CString GUEST_IP_ADDR;
char buff[100];
int REF;
virtual void OnReceive(int nErrorCode);
};
这样同时完成了对数据的接收,也顺便向主对话框发送了一个消息(UDP_RECEIVE消息,自己定义的一个消息,可以参考之前的消息传递博客),告诉主对话框相应的响应:
LRESULT CMFCUDPDlg::On_UDP_RECEIVE(WPARAM wParam, LPARAM lParam)
{
// CCreateContext *pContext = new CCreateContext;
CString str(m_socket.buff);
MessageBox(str);
STATE_T.SetWindowTextW(_T("正在获取消息!"));
return LRESULT();
}
此时实验效果为:
可以看到,成功接收到了来自网络调试助手的信息。
最后,我们把接收到的消息保存到CSV中去
LRESULT CMFCUDPDlg::On_UDP_RECEIVE(WPARAM wParam, LPARAM lParam)
{
// CCreateContext *pContext = new CCreateContext;
CString str =L"";
CString temp_str=L"";
//保存数据到指定路径
CStdioFile write_data_file;
if (!write_data_file.Open(SAVE_pathName, CFile::modeWrite | CFile::modeCreate))
{
write_data_file.Close();
}
else
{
for (int i = 0; i < m_socket.REF; i++) {
if (i == m_socket - 1) {
temp_str.Format(_T("%d\0"), m_socket.buff[i]);
}
else {
temp_str.Format(_T("%d,"), m_socket.buff[i]);
}
str = str + temp_str;
}
write_data_file.WriteString(str + "\n");
}
STATE_T.SetWindowTextW(_T("已成功接收消息!"));
return LRESULT();
}
注意保存时如果你使用的是%d表示,则你实际保存的是10进制数据。
效果为: