JNI_day02
二级指针
指向指针变量的指针,保存指针的地址
结构体
struct Student //struct Stdent 学生结构体类型
{
int id;//成员
char name[20];
int age;
float score;
};
其中,Student为结构体名,struct Student表示结构体类型,相当于int等基本数据类型
访问结构体变量中的成员变量
(p).id = 3 <=> stu.id <=> p->id = 3
其中->为指向运算符,用于给结构体指针变量访问其指向结构体变量中的成员变量
函数指针
表示:函数在代码段的起始地址,函数入口地址
函数指针变量:函数的入口地址
同样,函数名也代表函数的入口地址
void funA();//函数声明
int funB(int a,int n);//函数声明
void (pfA)();//函数指针变量,可以保存funA地址
int (pfB)(int *,int);//函数指针变量的定义,可以保存funB函数的入口地址
结构体和联合体
结构体类型使用sizeof运算符计算出所占用空间大小为结构体中成员变量分别占用的大小总和
联合体类型使用sizeof运算符计算出所占用空间的大小为联合体中所占空间最大的那个类型
JNI开发流程
一、编码
1.创建Android工程,用native声明本地方法
2.在工程中新建jni目录,创建.c的源文件
include <jni.h>
/** jni规定 本地方法名 Java_调用本地方法类所在的包名_类名_方法名
JNIEnv * env java环境,提供函数供调用
jobject obj 调用本地方法的对象
typedef const struct JNINativeInterface* JNIEnv;
JNIEnv <=> struct JNINativeInterface*
env : JNIEnv * <=> struct JNINativeInterface**
(*env)->NewStringUTF();
*/
jstring Java_com_itheima_helloworld_MainActivity_helloFromC(JNIEnv *env, jobject obj){//jstring (NewStringUTF)(JNIEnv, const char*); 把C字符串转化为java中字符串
// 把C字符串转化为java中字符串
return (*env)->NewStringUTF(env,"hello world");
}
二、编译
3.在jni目录下新建Android.mk文件
LOCAL_PATH := $(call my-dir) #提定当前路径
include $(CLEAR_VARS) #清除全局配置变量,LOCAL_XXX,除了LOCAL_PATH
LOCAL_MODULE := hello #指定生成动态库名hello,生成的动态库文件libhello.so
LOCAL_SRC_FILES := hello.c #指定生成动态库的源文件
include $(BUILD_SHARED_LIBRARY) #提定生成动态库
4.在jni目录下用ndk-build命令编译生成.so动态库(需要把ndk-build工具路径添加到系统path环境变量中)
5.在类中加载动态库
static{
System.loadLibrary("hello");//加载动态库名而不动态库文件名
}
JNI开发过程中的常见错误
a.找不到动态库
解决方案:库名错误或者生成的动态库与运行平台不符
b.找不到方法
解决方案:检查JNI的方法名是否符合规则或者Java调用的方法是否正确
javah命令的使用
a.在jdk1.6中,需要在工程的classes目录下执行,生成头文件
b.在jdk1.7中,需要在工程的src目录下执行,生成头文件
结合Eclipse和NDK的JNI开发流程
- 1.新建Android工程,声明本地方法
- 2.指定工程添加 add Native suport,修改其中源文件后缀为.c,在Android.mk文件中也要修改,见gif图片add ndk location2.gif
- 3.指定jni.h头文件路径见gif图片include jni head file.gif
- 4.进入工程src目录执行javah命令(jdk1.7),进入工程bin\classes执行javah。把jni函数声明拷贝到.c源文件中
- 5.实现本地jni函数
- 6.在调用类中加载动态库
Java反射的复习
//1.装载字节码
Class<?> clazz = Demo.class.getClassLoader().loadClass("Dialog");
//2.查找方法
Method method = clazz.getDeclaredMethod("showDialog", String.class);
//3.调用方法
method.invoke(clazz.newInstance(), "利用反射调用Dialog中的showDialog方法");
C调用Java中的方法(类似Java中的反射)
//1.find class
//jclass (FindClass)(JNIEnv, const char);
jclass clazz = (env)->FindClass(env,"com/demo/alipay01/MainActivity");
//2.get method id
//jmethodID (GetMethodID)(JNIEnv, jclass, const char, const char);
jmethodID methodid = (env)->GetMethodID(env, clazz, "showDialog", "(Ljava/lang/String;)V");
//3.call void methoid
//void (CallVoidMethod)(JNIEnv, jobject, jmethodID, ...);
(env)->CallVoidMethod(env, obj, methodid, "yong hu mi ma");
JNI_day02的更多相关文章
随机推荐
- 2.2 Go变量类型
内置类型 值类型: bool 布尔类型 int(32 or 64), int8, int16, int32, int64 整数类型 uint(32 or 64), uint8(byte), uint1 ...
- JSP知识点回顾
- URL特殊字符转义
在URL中,某些特殊字符会被转义成其它项,为了使这些特殊字符能正确表达,需用%加该字符的ASCII码在URL中显示.
- js 滚动条滑动
toTop() { let top = document.documentElement.scrollTop || document.body.scrollTop; // 实现滚动效果 const t ...
- 基于Unity实现像素化风格的着色器
Shader "MyShaderTest/SimplePixelationShader" { Properties { _MainTex ("Base (RGB)&quo ...
- [不得不知道系列]Java线程面试你不得不知道的基础知识一
Java内存管理面试指南一 Java基础面试指南一 Java基础面试指南二 Java基础面试指南三 Java基础面试指南四 Java线程面试指南一 Java线程面试指南二 Redis面试指南一 Kaf ...
- SEPC:使用3D卷积从FPN中提取尺度不变特征,涨点神器 | CVPR 2020
论文提出PConv为对特征金字塔进行3D卷积,配合特定的iBN进行正则化,能够有效地融合尺度间的内在关系,另外,论文提出SEPC,使用可变形卷积来适应实际特征间对应的不规律性,保持尺度均衡.PConv ...
- 【转发】基本adbui命令使用 可做图像识别
原文请参考,很详细:hao1032/adbui 非常详细,感谢整理!!首先了解下 adb命令大全,adb最全的命令
- Python 为什么不用分号作终止符?
一般而言,编程语言中使用分号";"来实现两种目的: 作为语句分隔符:使用分号来分隔语句(statement),这样就能在一行代码中书写多条语句(一行多句) 作为语句终止符:使用分号 ...
- [批处理教程之Shell]001.文本处理
在计算机科学中,Shell俗称壳(用来区别于核),是指“提供使用者使用界面”的软件(命令解析器).它类似于DOS下的command和后来的cmd.exe.它接收用户命令,然后调用相应的应用程序. 同时 ...