【问题标题】:How to build and use a C++ static library for ios application如何为 ios 应用程序构建和使用 C++ 静态库
【发布时间】:2013-09-15 09:59:10
【问题描述】:

我知道如何在 xcode 4.6 中使用 iOS->Framework&Library->Cocoa Touch Static Library 构建对象 C 静态库,在本教程 Creating a Static Library in iOS Tutorial 的帮助下,这很简单。然而,我不确定的一件事是如何为 io 应用程序构建和使用纯 C++ 静态库。搭建C++静态库,我也是用iOS->Framework&Library->Cocoa Touch Static Library的方针,不同的是我在创建静态库项目的时候把.h和.m文件都删了,然后把C++静态库头文件和实现文件都放到了在项目中。一个非常简单的例子如下:

你好.h

#include <iostream>
void say_hello();

你好.cpp

#include "hello.h"

void say_hello()
{
std::cout<<"hello"<<std::endl;
}

它似乎有效,我可以为 iPhone 6.1 模拟器构建 hello.a 静态库。下一步是构建一个将调用静态库的应用程序。我为 iPhone 6.1 Simulator 构建了一个简单的iOS application-&gt;Single View Application,然后尝试使用以下代码调用ViewController.mm 文件中的hello.a 静态库(将 ViewController.m 更改为 ViewController.mm 以便它可以调用 C++ 函数) :

say_hello();

但是,我收到了一条警告和两条错误消息:

警告:

ld: warning: ignoring file hello.a, file was built for archive which is not the architecture being linked (i386): 

错误 1:

hello.a
Undefined symbols for architecture i386:
  "say_hello()", referenced from:
      -[ViewController viewDidLoad] in ViewController.o

错误 2:

ld: symbol(s) not found for architecture i386
clang: error: linker command failed with exit code 1 (use -v to see invocation)

然后我有几个与这个实验有关的问题:

  • 创建纯C++静态库的方法正确吗?
  • 我调用 C++ 静态的方式有问题吗 图书馆?

  • 在我的示例中,调用静态库时,如何解决链接错误?

非常感谢。

【问题讨论】:

  • 我认为您使用正确的技术来构建静态库。你能确认一下你的静态库的 Build Settings->Architecture 吗?

标签: c++ ios objective-c xcode static-libraries


【解决方案1】:

这样就可以了,

1)用同样的方法创建c++库,iOS->Framework&Library->Cocoa Touch Static Library in Xcode 6.

TestCPlusPlus.h

int sub(int a, int b);

TestCPlusPlus.cpp

int sub(int a, int b)
{
 return a - b;
}

2) 构建静态库保持配置iOS设备,然后iPhone 6(基本上是模拟器。)

3) 然后在文件浏览器视图中展开产品。选择您的 .a 文件,例如 libTestStaticLibrary.a ,然后选择右键 > 在 Finder 中显示。在文件夹中向上移动。您应该能够看到两个文件夹 Debug-iphoneos 和 Debug-iphonesimulator

4) 现在 打开终端到此产品路径,然后输入

lipo -create Debug-iphoneos/libTestStaticLibrary.a Debug-iphonesimulator/libTestStaticLibrary.a -output libTestStaticLibrary.a

5) 现在打开你使用这个库的项目,你需要拖放静态库文件以及有静态库函数的函数声明的头文件。

6) 现在,创建 Cocoa touch 类文件,它将充当静态库和目标 -c 文件之间的适配器。将扩展名更改为 .mm

MyCustomAdaptor.h

@interface MyCustomAdaptor : NSObject

-(int)getSub:(int ) a SecondParam:(int) b;

@end

MyCustomAdaptor.mm

#import "TestCPlusPlus.h"

@implementation MyCustomAdaptor

-(int)getSub:(int ) a SecondParam:(int) b
{
 int c = sub(a,b);
 return c;
}

@结束

7) 现在在任何目标 c- 文件中使用这个 MyCustomAdaptor。

【讨论】:

  • +1。但是 Swift 中使用的相同方法呢?我已经实现了这个,但是使用 Bridging-Header.h 。这可以在没有桥接头的情况下简化吗?
【解决方案2】:

请注意您的 .a 是使用 i386 还是 armv7 构建的? 通常,您应该构建两个版本并将它们合并为一个。 像这样: lipo -create -output libopencore-amrwb.a libopencore-amrwb-armv7.a libopencore-amrwb-i386.a

【讨论】:

    【解决方案3】:

    我现在和你一样。我遇到了与您在此处描述的相同的问题,实际上是相同的两个错误。

    在构建库时,您必须牢记要在哪里使用它,iOS 设备或模拟器。 这很重要,因为您必须针对不同的情况进行构建,这非常简单,当您构建库时只需检查“选择方案”即可。

    真实设备使用:

    只是为了在模拟器中测试使用:

    构建后只需将创建的文件拖放到要使用库的项目中即可!

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多