这可能是一个菜鸟问题但是我到处搜索,我找到的唯一答案是包括标准的lib,这不是我的问题。
我正在编写一个需要向API发出http请求的程序,如果没有这个类,即使使用std库,程序编译也很好但是当初始化httpclient并编译链接器时会说这些错误;
Error LNK2001 unresolved external symbol __invalid_parameter_noinfo_noreturn Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\Pogobot.obj 1
Error LNK2001 unresolved external symbol ___std_exception_copy Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\libcpmt.lib(xthrow.obj) 1
Error LNK2001 unresolved external symbol ___std_exception_copy Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(throw_bad_alloc.obj) 1
Error LNK2001 unresolved external symbol ___std_exception_destroy Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\libcpmt.lib(xthrow.obj) 1
Error LNK2001 unresolved external symbol ___std_exception_destroy Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(throw_bad_alloc.obj) 1
Error LNK2001 unresolved external symbol __CxxThrowException@8 Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\libcpmt.lib(xthrow.obj) 1
Error LNK2001 unresolved external symbol __CxxThrowException@8 Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(throw_bad_alloc.obj) 1
Error LNK2001 unresolved external symbol __callnewh Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(new_scalar.obj) 1
Error LNK2001 unresolved external symbol _malloc Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(new_scalar.obj) 1
Error LNK2001 unresolved external symbol _free Pogobot C:\Visual Studio 2017\projects\Pogobot\Pogobot\LIBCMT.lib(delete_scalar.obj) 1
我的http类
#pragma once
#ifndef HTTP_CLIENT_H_
#define HTTP_CLIENT_H_
#include <iostream>
#include <string>
#include <thread>
#include <unordered_map>
#include <functional>
#define _WINSOCK_DEPRECATED_NO_WARNINGS 1
#include <winsock2.h>
#include <Windows.h>
#include <ws2tcpip.h>
#include "conio.h"
using namespace std;
#pragma comment(lib,"ws2_32.lib")
class HttpClient {
private:
unordered_map<string, string> params;
string hostName;
string requestPath;
int method = 2;
thread *requestThread;
public:
static const int POST = 1, GET = 2;
void sendAsync(string host, function<void(string, string)> onResponse) {
requestThread = new thread(&HttpClient::_send, this, host, onResponse);
}
void sendSync(string host, function<void(string, string)> onResponse) {
return _send(host, onResponse);
}
void waitForResult() {
requestThread->join();
}
void setParam(string key, string val) {
params[key] = val;
}
void setMethod(int method) {
this->method = method;
}
void setPath(string path) {
this->requestPath = path;
}
void _send(string host, function<void(string, string)> onResponse) {
hostName = host;
WSADATA wsa;
if (WSAStartup(514, &wsa) != 0) {
return;
}
struct addrinfo *result = NULL, *ptr = NULL, hints;
SOCKET ConnectSocket = INVALID_SOCKET;
ZeroMemory(&hints, sizeof(hints));
hints.ai_family = AF_UNSPEC;
hints.ai_socktype = SOCK_STREAM;
hints.ai_protocol = IPPROTO_TCP;
if (getaddrinfo(host.c_str(), "80", &hints, &result) != 0) {
return;
}
for (ptr = result; ptr != NULL; ptr = ptr->ai_next) {
ConnectSocket = socket(ptr->ai_family, ptr->ai_socktype, ptr->ai_protocol);
if (ConnectSocket == INVALID_SOCKET) {
WSACleanup();
return;
}
if (connect(ConnectSocket, ptr->ai_addr, (int)ptr->ai_addrlen) == SOCKET_ERROR) {
closesocket(ConnectSocket);
ConnectSocket = INVALID_SOCKET;
continue;
} else {
string request;
if (method == HttpClient::GET) {
request += "GET ";
request += requestPath;
request += '?';
for (auto r : params) {
request += r.first;
request += "=";
request += r.second;
}
request += " HTTP/1.0\r\n";
request += "Host: ";
request += hostName;
request += "\r\n\r\n";
}
else if (method == HttpClient::POST) {
request += "POST ";
request += requestPath;
request += " HTTP/1.0\r\n";
string paramsString;
for (auto r : params) {
if (paramsString.size()) paramsString += '&';
paramsString += r.first;
paramsString += "=";
paramsString += r.second;
}
request += "Host: ";
request += hostName;
request += "\r\n";
request += "Content-Length: ";
request += to_string(paramsString.size());
request += "\r\n";
request += paramsString;
request += "\r\n";
} else {
return;
}
::send(ConnectSocket, request.c_str(), request.size(), 0);
char *header = new char[4096];
int headerLen = ::recv(ConnectSocket, header, 4096, 0);
header[headerLen] = 0;
string headerString(header);
unsigned contentLenPos = headerString.find("Content-Length:");
if (contentLenPos == string::npos) {
return;
}
unsigned contentLenEndPos = headerString.find('\n', contentLenPos);
string ln = headerString.substr(contentLenPos + 15, contentLenEndPos - contentLenPos - 15);
int blen;
if (!(ln[0] == '"' || (ln[0] < 58 && ln[0]>47))) {
blen = 4096;
} else {
blen = stoi(ln);
}
char *body = new char[blen + 1];
int bodyLen = ::recv(ConnectSocket, body, blen, 0);
body[bodyLen] = 0;
onResponse(header, body);
closesocket(ConnectSocket);
break;
}
}
}
};
#endif
我的其余代码可以工作,但是当尝试发出http请求时,链接器说基本的C功能没有得到解决,我无法弄清楚原因。令我困惑的是为什么像free()和memcpy()这样的函数没有得到解决。
编辑1:我设置了详细的链接器topo,看看它的搜索位置,这是输出。
1>Searching libraries
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\ws2_32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\kernel32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\user32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\gdi32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\winspool.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\comdlg32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\advapi32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\shell32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\ole32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\oleaut32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\uuid.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\odbc32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\odbccp32.lib:
1> Searching C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\VC\Tools\MSVC\14.11.25503\lib\x86\libcpmt.lib:
1> Searching C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\VC\Tools\MSVC\14.11.25503\lib\x86\LIBCMT.lib:
1> Searching C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\VC\Tools\MSVC\14.11.25503\lib\x86\OLDNAMES.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\ws2_32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\kernel32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\user32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\gdi32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\winspool.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\comdlg32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\advapi32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\shell32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\ole32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\oleaut32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\uuid.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\odbc32.lib:
1> Searching C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\lib\odbccp32.lib:
1> Searching C:\Program Files (x86)\Microsoft Visual Studio\2017\Enterprise\VC\Tools\MSVC\14.11.25503\lib\x86\libcpmt.lib: