Arduino类出现多重函数定义警告,编译失败求助
Visual Studio/Visual Micro编译Arduino项目多重定义错误排查与解决
编译失败,错误信息如下:
Command.cpp.o (symbol from plugin)*: In function CommandClass::CommandClass() (.text+0x0)*: multiple definition of CommandClass::JsonToClass(String) Command.cpp.o (symbol from plugin)*: (.text+0x0): first defined here
CommandClass类位于项目引入的Arduino库SWRAntennaLib中,项目文件SWRArduino2.vcxproj的ItemGroup条目如下:
<ItemGroup> <ClCompile Include="..\..\libraries\SWRAntennaLib\src\Command.cpp" /> <ClCompile Include="..\..\libraries\SWRAntennaLib\src\Enms.cpp" /> <ClCompile Include="AllBands.cpp" /> <ClCompile Include="Band.cpp" /> <ClCompile Include="FileReqestHandler.cpp" /> <ClCompile Include="FileRequest.cpp" /> <ClCompile Include="Frequency.cpp" /> <ClCompile Include="Json.cpp" /> <ClCompile Include="LCD.cpp" /> <ClCompile Include="RTClock.cpp" /> <ClCompile Include="SDCard.cpp" /> <ClCompile Include="Stepper.cpp" /> <ClCompile Include="SWRArduino2.ino"> <FileType>CppCode</FileType> <DeploymentContent>true</DeploymentContent> </ClCompile> </ItemGroup> <ItemGroup> <None Include="src\arduino folders read me.txt"> </None> </ItemGroup> <ItemGroup> <ProjectCapability Include="VisualMicro" /> </ItemGroup> <ItemGroup> <ClInclude Include="..\..\libraries\SWRAntennaLib\src\Command.h" /> <ClInclude Include="..\..\libraries\SWRAntennaLib\src\DefinedValues.h" /> <ClInclude Include="..\..\libraries\SWRAntennaLib\src\Enms.h" /> <ClInclude Include="AllBands.h" /> <ClInclude Include="Band.h" /> <ClInclude Include="FileReqestHandler.h" /> <ClInclude Include="FileRequest.h" /> <ClInclude Include="Frequency.h" /> <ClInclude Include="Json.h" /> <ClInclude Include="LCD.h" /> <ClInclude Include="RTClock.h" /> <ClInclude Include="SDCard.h" /> <ClInclude Include="Stepper.h" /> <ClInclude Include="__vm\.SWRArduino2.vsarduino.h" /> </ItemGroup>
Command.h代码
#include <ArduinoJson.h> #include<RTClib.h> class CommandClass { protected: void JsonToClass(String json); String _commandAction; String _request; String _timeStamp; public: CommandClass(); CommandClass(String command); CommandClass(String action, String request); const String ToJson(); String CommandAction(String value = ""); String Request(String value = ""); String TimeStamp(String value = ""); }; extern CommandClass Command;
Command.cpp代码
#include "Command.h" CommandClass::CommandClass(){} CommandClass::CommandClass(String command) { _timeStamp = DateTime().TIMESTAMP_FULL; JsonToClass(command); } CommandClass::CommandClass(String action, String request) { _timeStamp = DateTime().TIMESTAMP_FULL; _commandAction = action; _request = request; } void CommandClass::JsonToClass(String json) { // Deserialize the JSON document JsonDocument doc; DeserializationError error = deserializeJson(doc, json); if (error) { Serial.print(F("deserializeJson() failed: ")); Serial.println(error.f_str()); return; } // Command values _commandAction = doc["commandAction"].as<String>(); _request = doc["request"].as<String>(); _timeStamp = doc["timeStamp"].as<String>(); } const String CommandClass::ToJson() { // Create a new JSON document JsonDocument doc; // Set the values doc["commandAction"] = _commandAction; doc["request"] = _request; doc["timeStamp"] = _timeStamp; // Serialize the JSON document String json; serializeJson(doc, json); return json; } String CommandClass::CommandAction(String value) { if (value != "") { _commandAction = value; } return _commandAction; } String CommandClass::Request(String value) { if (value != "") { _request = value; } return _request; } String CommandClass::TimeStamp(String value) { if (value != "") { _timeStamp = value; } return _timeStamp; } CommandClass Command;
解决方法
- 移除重复的源文件引用:Visual Micro会自动识别并添加库的源文件到编译列表,若你手动在vcxproj中又包含了
Command.cpp和Enms.cpp,会导致同一文件被多次编译。打开vcxproj文件,删除<ClCompile Include="..\..\libraries\SWRAntennaLib\src\Command.cpp" />和<ClCompile Include="..\..\libraries\SWRAntennaLib\src\Enms.cpp" />这两行。 - 添加头文件保护:修改Command.h,加入头文件保护宏,避免因多次包含头文件导致的隐式重复声明:
#ifndef COMMAND_H #define COMMAND_H // 原Command.h内容不变 #endif // COMMAND_H
- 确认全局实例唯一性:检查项目中所有源文件,确保只有Command.cpp中定义了
CommandClass Command;,其他文件仅通过extern CommandClass Command;引用该实例,无重复定义。 - 清理编译缓存:执行Visual Studio的
Clean Solution操作,同时删除项目目录下的__vm文件夹和Arduino编译缓存(通常在%LOCALAPPDATA%\Arduino15或项目的build目录),之后重新编译项目。
内容的提问来源于stack exchange,提问作者BedfordNYGuy
相关产品推荐
相关产品推荐

