Java 调用 C/C++
C/C++ 本地语言 特点 平台相关性强
windows上编写 能在linux上运行的 本地代码
交叉编译 在一个平台上编译出另一个平台可以执行的本地代码
平台 CPU平台 X86(Intel AMD) ARM(高通骁龙 华为 海思 麒麟 三星 MTK)99%android设备
mips 嵌入式设备上
操作系统平台 windows linux max OS unix 类unix
不同平台支持的native code不同
交叉编译的原理就是在一个平台上模拟另外一个平台的特点进行编译
在windows上编写能够在android上运行的本地代码
NDK native develop kit

NDK开发相关文档&案例下载
https://developer.android.google.cn/ndk/index.html
JNI开发通用流程 NDK-BUILD(studio eclipse都可以使用的方法)
①在java代码中声明native 方法 native方法没有实现
//用native关键字声明本地方法 本地方法不用实现 public native String helloFromC();②在模块根目录下(如果是eclipse就是在项目的根目录下)创建jni文件夹,在文件夹中创建.c的源代码
#include<stdio.h>#include<stdlib.h>#include<jni.h>//// Created by fullcircle on 2017/2/18.////java程序还是应用的入口 在C中只是实现一些函数 等待着java去调用//native函数命名规则 Java_包名_类名(包含native方法的java类)_native方法名//JNIEnv* env//JNIEnv 是结构体 JNINativeInterface的一级指针//env是JNIEnv的一级指针 所以env就是结构体JNINativeInterface的二级指针//JNINativeInterface 这个结构体中声明了大量的函数指针 这些函数指针在Jni开发中做用非常重要//jobject thiz 哪个java对象通过jni调用到这个方法 这个jobject 就是这个java对象//对于当前的案例来说 这个jobject就是MainActivity//jstring Java_com_example_hellojni_HelloJni_stringFromJNI( JNIEnv* env,// jobject thiz )//JNIEnv* env,jobject thiz 这两个参数是必须传入的jstring Java_com_itheima_jni97_MainActivity_helloFromC(JNIEnv* env,jobject thiz){ char* cstr = "hello from c!!!!"; //NewStringUTF 作用把c的字符串(char* 类型)转换成java的字符串//jstring (*NewStringUTF)(JNIEnv*, const char*); //return (**env).NewStringUTF(env, cstr); return (*env)->NewStringUTF(env, cstr);}

#LOCAL_PATH 获取当前路径LOCAL_PATH := $(call my-dir)# 清除上次编译获取的编译环境变量 会保存LOCAL_PATHinclude $(CLEAR_VARS)#指定编译生成的模块叫什么名字LOCAL_MODULE := hello-jni#指定要编译的.c源文件叫什么名字LOCAL_SRC_FILES := hello.c#生成动态链接库 .so文件include $(BUILD_SHARED_LIBRARY)⑤在运行之前 需要通过System.loadLibrary加载.so文件 注意加载.so文件 文件名字不包含lib前缀和.so后缀
⑥如果是studio环境 需要在模块的.gradle文件中加上如下内容
sourceSets.main.jniLibs.srcDirs = [‘libs‘] 放到android{}中
JNI开发常见错误
①Caused by: java.lang.UnsatisfiedLinkError: Native method not found 本地方法没有找到
出现原因 c函数名字 不符合 Native函数的命名规则
解决办法 用javah生成头文件
javah使用方法 到模块的src/main/java 目录下运行javah
格式 javah 包含native方法的java类的全类名
原因2忘记使用System.loadlibrary加载.so文件
解决办法:使用静态代码块在Activity加载的时候就把.so文件加载进来
static { System.loadLibrary("hello-jni"); }出现原因 在System.loadlibrary加载.so文件 文件名字写错
原因2 当前的.so不支持设备的cpu平台 解决方法 在jni目录下创建Application.mk 指定当前应用的.so支持哪些cpu平台
APP_ABI := armeabi x86如果使用NDK-build做jni开发 Android.mk Appliction.mk 尽量ctrl+c ctrl+V
studio中NDK-Build简便流程
①在java代码中声明native方法
②在main目录下创建jni目录 并且创建一个Android.mk
③右键单击模块 选择如下内容
![技术分享]()
android{......externalNativeBuild { ndkBuild { path ‘src/main/jni/Android.mk‘ } }}

![技术分享]()

原文:http://www.cnblogs.com/Oldz/p/6886448.html