Android NDK编程(一)

        在标准的JAVA平台下,每一个Process都可以产生很多JAVA VM对象,每一个JAVA VM都有一个与之对应的JAVA VM对象,但是在Android平台上,每一个Process只可以产生一个Dalvik VM对象,也就是说一个Android中的进程有且只有一个虚拟机对象来服务所有的JAVA/C/C++代码

        JNIEnv*内部包含一个Pointer,Pointer指向Dalvik虚拟机的JAVA VM对象的Function Table,JNIEnv*关于程序执行环境的众多函数正是来源于Dalvik虚拟机。

Android中每一个JAVA线程第一个调用本地C/C++代码时,Dalvik虚拟机实例会为这个线程产生一个JNIEnv * 指针。

        安装完Cygwin、NDK之后就可以开发程序了。

        首先编写JAVA代码,新建一个安卓工程,本地方法要在函数名前加Native关键字声明,同时在static代码块中加载本地动态链接库。

package com.example.hellojni;

import android.app.Activity;
import android.os.Bundle;
import android.widget.TextView;

public class HelloJNI extends Activity {
	
	static{
    	System.loadLibrary("hello-jni");
    }    
	
	public native String hello();
	
	public native boolean isPrime(int num);
	
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);        
        TextView tvBox = new TextView(HelloJNI.this);
        StringBuilder msgBuilder = new StringBuilder();
        msgBuilder.append(hello()).append("\n");
        msgBuilder.append(isPrime(12)).append("\n");
        
        tvBox.setText(msgBuilder.toString());
        setContentView(tvBox);
    }                  
}

        然后,打开命令行Cmd,进入工程根目录,执行命令生成C代码的头文件,这一步主要是利用javah命令来帮助我们生成函数名,因为JNI是一个协议,对函数名称有苛刻的要求,我们用javah来生成,然后复制一下就相当方便了!当然,如果你闲的慌,也可以根据要求自己手写哦。

javah -classpath bin/classes -d jni com.example.hellojni.HelloJNI
        我们刷新一下工程目录,就会工程下面出现了jni目录,打开它,就出现了我们想要的头文件:com_example_hellojni_HelloJNI.h,复制一下里面的函数名,在jni目录下新建hello-jni.c文件。这里要注意文件名和之前在java中LoadLibrary的参数相同。

#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <jni.h>
#include <assert.h>


#include <android/log.h>
#define LOG_TAG "NDK study"
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, LOG_TAG, __VA_ARGS__)
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__)


/*
 * Class:     com_example_hellojni_HelloJNI
 * Method:    hello
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_com_example_hellojni_HelloJNI_hello
  (JNIEnv * env, jobject jobj)
{
	return (*env)->NewStringUTF(env, "Hello, Android NDK");
}

/*
 * Class:     com_example_hellojni_HelloJNI
 * Method:    isPrime
 * Signature: (I)Z
 */
JNIEXPORT jboolean JNICALL Java_com_example_hellojni_HelloJNI_isPrime
  (JNIEnv * env, jobject jobj, jint number)
{
	LOGI("Java_com_example_hellojni_HelloJNI_isPrime called!");
	jint i = 0;
	jboolean bPrime = JNI_TRUE;
	for( i = 2; i < number; i++){
		if(number % i == 0){
			bPrime = JNI_FALSE;
			break;
		}
	}
	return bPrime;
}
好了,代码写完了,编写Makefile文件。在Android中,Makefile文件名为Android.mk。同样,在jni目录下新建Android.mk文件,这里我也是抄的,修改一下文件名!

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE    := hello-jni
LOCAL_SRC_FILES := hello-jni.c
LOCAL_LDLIBS 	:= -llog

include $(BUILD_SHARED_LIBRARY)

        现在,只需要编译一下C语言文件就可以了,运行

$NDK/ndk-build
        命令即可。相信你环境已经配好了。


        运行Android程序即可。







评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值