45

我正在尝试将 Objective-C 与 C++ 混合。当我编译代码时,我得到了几个错误。

#import <Cocoa/Cocoa.h>
#include "B.h"

@interface A : NSView {
    B *b;
}

-(void) setB: (B *) theB;

@end

#import "A.h"

@implementation A

- (id)initWithFrame:(NSRect)frame {
    self = [super initWithFrame:frame];
    if (self) {
        // Initialization code here.
    }
    return self;
}

- (void)drawRect:(NSRect)dirtyRect {
    // Drawing code here.
}

-(void) setB: (B *) theB {
    b = theB;
}

@end

溴化氢

#include <iostream>

class B {

    B() {
        std::cout << "Hello from C++";
    }

};

以下是错误:

/Users/helixed/Desktop/Example/B.h:1:0 /Users/helixed/Desktop/Example/B.h:1:20: error: iostream: No such file or directory
/Users/helixed/Desktop/Example/B.h:3:0 /Users/helixed/Desktop/Example/B.h:3: error: expected '=', ',', ';', 'asm' or '__attribute__' before 'B'
/Users/helixed/Desktop/Example/A.h:5:0 /Users/helixed/Desktop/Example/A.h:5: error: expected specifier-qualifier-list before 'B'
/Users/helixed/Desktop/Example/A.h:8:0 /Users/helixed/Desktop/Example/A.h:8: error: expected ')' before 'B'
/Users/helixed/Desktop/Example/A.m:26:0 /Users/helixed/Desktop/Example/A.m:26: error: expected ')' before 'B'
/Users/helixed/Desktop/Example/A.m:27:0 /Users/helixed/Desktop/Example/A.m:27: error: 'b' undeclared (first use in this function)
4

5 回答 5

78

您需要将.m文件命名为.mm。您将能够使用 Objective-C 编译 C++ 代码。

因此,按照您的示例,您的AView.m文件应命名为AView.mm。就这么简单。它工作得很好。我在 iPhone 项目中使用了很多 std 容器(std::vector、std::queue 等)和遗留 C++ 代码,没有任何复杂性。

于 2010-04-26T00:24:31.623 回答
5

没关系,我觉得自己很傻。您所要做的就是将 AView.m 重命名为 AView.mm,以便编译器知道它是 Objective-C++,并且它可以毫无问题地编译。

于 2010-04-26T00:24:33.793 回答
2

您可以通过 C++ 类的前向声明来保持接口清洁:

#import <AnObjCclass.h>
class DBManager; // This is a C++ class. NOTE: not @class

@interface AppDelegate : UIResponder <UIApplicationDelegate,
                                    CLLocationManagerDelegate,
                                    MFMailComposeViewControllerDelegate>
{
    DBManager* db;
...
}
于 2012-07-01T15:13:58.477 回答
1

我正在分享我对这个主题的理解的一些观点。

我们可以将 .cpp 和 .m 文件与纯 C 接口混合使用。我们知道 Clang 编译器将支持 C++、Objective C 以及 Objective C++,它可能是混合这些语言的更好方法。

混合这些语言时要注意的一件事是使用头文件。通过在类扩展中声明 Cpp 对象,我们可以将 C++ 排除在 Objective C 头文件之外。

或者,我们可以在 Objective Cpp(.mm) 文件中的 @implementation 块的开头声明 cpp 对象。

当我们处理 Cpp 对象时,管理内存将是一个问题。我们可以使用“new”为对象分配内存,并通过调用“delete object”释放内存。通常,如果我们使用 ARC,我们不需要知道释放对象的内存。

在使用 cpp 类时,我们可以通过两种方式声明 Cpp 对象,即 CppWrapper 包装器和 CppWrapper *wrapper 其中 CppWrapper 是 Cpp 类。当我们使用后者时,程序员负责管理内存。

另一个主要的事情是,当我们调用带有参数的目标 C 方法时,我们正在传递引用,而在 cpp 中,我们需要使用 '&' 通过引用传递参数 关键字,否则传递对象的副本。

Objective C 对象的释放是在运行时处理的,当对 Cpp 对象调用“删除”时,它将不再保留在内存中。

在编写 Cpp 时,我们有共享指针和弱指针,类似于 Objective C 中的强弱指针。

http://philjordan.eu/article/mixing-objective-c-c++-and-objective-c++ http://www.raywenderlich.com/62989/introduction-c-ios-developers-part-1

于 2014-07-27T19:32:10.403 回答
0

在您希望引入一个简单的 C++ 函数的情况下,std::cout <<Hot Licks 提供了一个很好的选择。

Identity and Type将“ ”从:更改Objective-C source为:Objective-C++ source

.mm 扩展名只是标识文件类型;然后你正在寻找一个 Objective-C++ 而不是一个 Objective-C 类型。

于 2013-08-11T20:25:58.193 回答