我们定义了一些方法,以在需要时允许临时控制台输入。这些方法包含在名称空间中,并定义并使用一个类来执行实际工作。
为简洁起见,对这些定义进行了简化:
ConsoleInput.h
#include <cstddef>
#include <map>
#include <memory>
#include <vector>
namespace MyNameSpc
{
typedef std::vector<char> buffer_t;
class ConsoleInput
{
// Methods for windows and linux console input
}
int GetString(buffer_t &buffer, ...);
}
RequestInput.h
#include "ConsoleInput.h"
#include <cstddef>
#include <string>
namespace MyNameSpc
{
const std::string empty = std::string();
class RequestInputParam
{
// Methods
}
int RequestInput(buffer_t &buffer);
int RequestInput(buffer_t &buffer, const RequestInputParam ¶m);
// and other overloads
}
ConsoleInput.cpp
#include "ConsoleInput.h"
#include "RequestInput.h"
#include <cstddef>
#include <iostream>
#include <memory>
#include <string>
#include <fcntl.h>
#include <stdio.h>
// and other headers.
namespace MyNameSpc
{
// implements class ConsoleInput methods.
// Implements GetString()
}
RequestInput.cpp
#include "ConsoleInput.h"
#include "RequestInput.h"
#include <cstddef>
#include <iostream>
#include <memory>
#include <string>
namespace MyNameSpc
{
// implements the overloaded methods.
}
然后我们用#include RequestInput.h
来调用它们,然后再调用int retVal = MyNameSpc::RequestInput(...)
。当所有代码都是C ++时,这一切都很好。现在,我必须从最近放入我们的存储库的C代码中引用此代码。我不认为我可以(嗯,我可以,但是我认为它会破坏其他东西)只是将C代码编译为C ++,所以我确实确实需要以某种方式将其引入C。
当我尝试构建时,由于没有找到iostream标头,我遇到了一些初始错误。但是,在阅读了关于extern“ C”的信息后,当我将这些C ++标头包含在其中时,我不清楚如何继续进行操作。代码,类(我可能需要引用的唯一一个是参数类)和名称空间。
更新
我已查看了提供的链接,并试图利用来自here和here的信息。我没有成功。
RequestInputWrapper.h
#ifndef REQUEST_WRAPPER_H
#define REQUEST_WRAPPER_H
#include <stddef.h>
#include "RequestInput.h"
#ifdef __cplusplus
extern "C" {
#endif
typedef struct RequestInputParam RequestInputParam; // line 29
RequestInputParam* CreateRequestInputParam();
void DisposeRequestInputParam( RequestInputParam* pObject );
void C_AddMainPrompt(RequestInputParam *param, char *msg);
int C_RequestInputAllocPtr(char * * const ppInput,
unsigned int * const pInputLen);
int C_RequestInput(char * const pInput,
unsigned int * const pInputLen);
#ifdef __cplusplus
}
#endif
#endif /* REQUEST_WRAPPER_H */
RequestInputWrapper.cpp
#include "RequestInput.h"
#include "RequestInputWrapper.h" // line 13
#ifdef __cplusplus
extern "C" {
#endif
RequestInputParam* CreateRequestInputParam()
{
return new RequestInputParam(); // line 25
}
void DisposeRequestInputParam( RequestInputParam* pObject ) // line 28
{
if ( pObject != NULL )
{
delete pObject; // line 32
pObject = NULL;
}
}
void C_AddMainPrompt(RequestInputParam *param, char *msg) { param->AddMainPrompt( msg ); }
int C_RequestInputAllocPtr(char * * const ppInput,
unsigned int * const pInputLen)
{
return RequestInput(ppInput, pInputLen);
}
int C_RequestInput(char * const pInput,
unsigned int * const pInputLen)
{
return RequestInput(pInput, pInputLen);
}
#ifdef __cplusplus
}
#endif
当前正在引发以下错误(我仅对C&P的第一部分进行重复,开始重复;行号与上面的代码不匹配,该代码已删除所有注释,因此我在注释中添加了注释行号):
cli/RequestInputWrapper.cpp: In function ‘RequestInputParam* CreateRequestInputParam()’:
cli/RequestInputWrapper.cpp:25:35: error: invalid use of incomplete type ‘RequestInputParam {aka struct RequestInputParam}’
return new RequestInputParam();
^
In file included from cli/RequestInputWrapper.cpp:13:0:
./Include/RequestInputWrapper.h:29:16: error: forward declaration of ‘RequestInputParam {aka struct RequestInputParam}’
typedef struct RequestInputParam RequestInputParam;
^
cli/RequestInputWrapper.cpp: In function ‘void DisposeRequestInputParam(RequestInputParam*)’:
cli/RequestInputWrapper.cpp:32:16: error: possible problem detected in invocation of delete operator: [-Werror]
delete pObject;
^
cli/RequestInputWrapper.cpp:28:6: error: ‘pObject’ has incomplete type [-Werror]
void DisposeRequestInputParam( RequestInputParam* pObject )
^
In file included from cli/RequestInputWrapper.cpp:13:0:
./Include/RequestInputWrapper.h:29:16: error: forward declaration of ‘struct RequestInputParam’ [-Werror]
typedef struct RequestInputParam RequestInputParam;
^
cli/RequestInputWrapper.cpp:32:16: note: neither the destructor nor the class-specific operator delete will be called, even if they are declared when the class is defined
delete pObject;
^
答案 0 :(得分:-1)
我怀疑文章中被建议为“重复项”的答案仅是书面形式,未经测试。经过更多搜索之后,我最终偶然发现了this answer,它提供了构建此文件所需的指导。
简而言之,我在我的C ++包装代码(facepalm)中缺少名称空间,并且我不得不添加reinterpret_cast调用。我还在typedef中更改了类型的名称...我以为它是在引用C ++类型(因为这至少是一个示例似乎显示的内容),但是,不……它必须是它自己的struct类型。
RequestInputWrapper.h
#ifndef REQUEST_WRAPPER_H
#define REQUEST_WRAPPER_H
#ifdef __cplusplus
extern "C" {
#endif
#include <stddef.h>
typedef struct C_RequestInputParam C_RequestInputParam;
C_RequestInputParam * CreateRequestInputParam();
void DisposeRequestInputParam( C_RequestInputParam *pObject );
void C_AddMainPrompt( C_RequestInputParam *param, char *msg);
int C_RequestInputAllocPtr( char * * const ppInput,
unsigned int * const pInputLen );
int C_RequestInput( char * const pInput,
unsigned int * const pInputLen );
#ifdef __cplusplus
}
#endif
#endif /* REQUEST_WRAPPER_H */
RequestInputWrapper.cpp
#include "RequestInput.h"
#include "RequestInputWrapper.h"
extern "C" {
C_RequestInputParam * CreateRequestInputParam()
{
return reinterpret_cast< C_RequestInputParam * >( new RequestInputParam() );
}
void DisposeRequestInputParam( C_RequestInputParam *pObject )
{
if ( pObject != NULL )
{
delete reinterpret_cast< MyNameSpc::RequestInputParam * >( pObject );
pObject = NULL;
}
}
void C_AddMainPrompt( C_RequestInputParam *param, char *msg )
{
reinterpret_cast< MyNameSpc::RequestInputParam * >( param )->AddMainPrompt( msg );
}
int C_RequestInputAllocPtr( char * * const ppInput,
unsigned int * const pInputLen )
{
return MyNameSpc::RequestInput( ppInput, pInputLen );
}
int C_RequestInput( char * const pInput,
unsigned int * const pInputLen )
{
return MyNameSpc::RequestInput( pInput, pInputLen );
}
}