调用 C++ | Swift

Swift 不能直接调用 C++,需要通过 Objective-C/C++ 桥接。本文主要介绍了在 Swift 中调用 C++ 的一些技巧。

调用函数

  1. 新建 C++ 文件,勾选生成头文件。
    1
    2
    3
    4
    5
    6
    7
    // CPPFile.hpp
    #include <stdio.h>

    class TestCPP {
    public:
    int add(int a, int b);
    };
1
2
3
4
5
6
// CPPFile.cpp
#include "CPPFile.hpp"

int TestCPP::add (int a, int b) {
return a + b;
}
  1. 新建 Objective-C 文件,此时 Xcode 会提示创建桥接文件,创建即可。这里我们需要调用的是 C++,所以还需要把 .m 文件(Objective-C)改为 .mm 文件(Objective-C++)。然后再新建一个头文件,这样就 Objective-C++ 部分就完成了。相关内容如下:
    1
    2
    // Project-Bridging-Header.h
    #import "OCFile.h"
1
2
3
4
5
6
// OCFile.h
#import <Foundation/Foundation.h>

@interface OCFile : NSObject
+ (int)sumWithNum: (int)a withNum: (int)b;
@end
1
2
3
4
5
6
7
8
9
10
// OCFile.mm
#import "OCFile.h"
#import "CPPFile.hpp"

@implementation OCFile
+ (int)sumWithNum: (int)a withNum: (int)b {
int sum = TestCPP.add(a, b)
return sum;
}
@end

注意

Xcode 默认把 .h 文件当做 Objective-C 而非 Objective-C++ 的头文件,所以在 .h 文件中不可以引用任何 C++ 头文件以及引用了 C++ 头文件的头文件,否则会提示 xxx not found。如果这个无法避免,可以考虑使用 opaque pointers

1
2
3
4
5
6
7
// CPPClass.h
class CPPClass {
public:
int getNumber() {
return 10;
}
};
1
2
3
4
5
6
7
8
// ObjCPP.h
struct CPPMembers;

@interface ObjCPP : NSObject {
// opaque pointer to store cpp members
struct CPPMembers *_cppMembers;
}
@end
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
// ObjCPP.mm
#import "ObjCPP.h"
#import "CPPClass.h"

struct CPPMembers {
CPPClass member1;
};

@implementation ObjCPP

- (id)init {
self = [super init];
if (self) {
_cppMembers = new CPPMembers;
NSLog(@"%d", _cppMembers->member1.getNumber());
}

return self;
}

- (void)dealloc {
delete _cppMembers;
}

@end

调用静态库

在 Xcode 编译中引入静态库的思路和 gcc/g++ 等编译器相同:首先需要指定库的名字,其次要指定库的路径。

  1. 指定库的名字:按照下图指示添加想要引入的静态库文件。
  2. 指定库和头文件的路径:在上一步操作的 Build Phases 旁边找到 Build Settings,然后搜索 “Search Paths”,在 Library Search Paths 中添加刚才引入的静态库在本机上的路径。在 Header Search Paths 中添加相应的头文件在本机上的路径。

参考

Swift呼叫C++(圖解版)
How to include C++ headers in an Objective C++ header?

作者

zhongtian

发布于

2020-02-04

更新于

2023-12-16

许可协议

评论