C调用java例子

原创 2018年04月14日 22:30:19

实验代码已打包,下载地址

实现原理:使用JNI提供的接口来反射得到Java方法,进行调用。jni.h在JDK里(jdk1.8.0_121/include/)。

(通过JNI可以实现java调用C,也可以实现C调用java)

 HelloWorld.java:

public class HelloWorld{
	public static void main(String[] args){
		System.out.println("Hello, World");
	}
	public static int square(int input){
		int output = input * input;
		return output;
	}
	public static int power(int input, int exponent){
		int output,i;
		output=1;
		for(i=0;i<exponent;i++){
			output *= input;
		}
		return output;
	}
}

hello_world.c:

#include<stdio.h>
#include<jni.h>

JNIEnv* create_vm(JavaVM **jvm)
{
    JNIEnv* env;
    JavaVMInitArgs args;
    JavaVMOption options;
    args.version = JNI_VERSION_1_6;
    args.nOptions = 1;
    options.optionString ="-Djava.class.path=./";
    args.options = &options;
    args.ignoreUnrecognized = 0;
    int rv;
    rv = JNI_CreateJavaVM(jvm,(void**)&env, &args);
    if (rv < 0 || !env)
        printf("Unable to Launch JVM%d\n",rv);
    else
        printf("Launched JVM! :)\n");
    return env;
}

 
void invoke_class(JNIEnv* env)
{
    jclass hello_world_class;
    jmethodID main_method;
    jmethodID square_method;
    jmethodID power_method;
    jint number=20;
    jint exponent=3;
    hello_world_class =(*env)->FindClass(env, "HelloWorld");
    main_method =(*env)->GetStaticMethodID(env, hello_world_class, "main","([Ljava/lang/String;)V");
    square_method =(*env)->GetStaticMethodID(env, hello_world_class, "square","(I)I");
    power_method =(*env)->GetStaticMethodID(env, hello_world_class, "power","(II)I");
    (*env)->CallStaticVoidMethod(env,hello_world_class, main_method, NULL);
    printf("%d squared is %d\n",number,
        (*env)->CallStaticIntMethod(env,hello_world_class, square_method, number));
    printf("%d raised to the %d power is%d\n", number, exponent,
        (*env)->CallStaticIntMethod(env,hello_world_class, power_method, number, exponent));
}


int main(int argc,char **argv)
{
    JavaVM *jvm;
    JNIEnv *env;
    env = create_vm(&jvm);
    if(env == NULL)
        return 1;
    invoke_class(env);
    return 0;
}

 # 编译java

javac HelloWorld.java

 # 编译C

gcc -D__int64="long long" -Ic:/java/jdk1.8.0_121/include/ -Ic:/java/jdk1.8.0_121/include/win32 -ohello_world hello_world.c -L c:/java/jdk1.8.0_121/jre/bin/server -ljvm

要点

a)     使用64位的JDK需要添加-D__int64="longlong"

b)     通过-I参数指定jni.h、jni_md.h的路径。

c)     通过-L指定jvm.dll的路径。

这3个文件都在JDK文件夹里面,可以通过搜索找到具体的路径。

 

#运行程序

hello_world

如果报找不到jvm.dll的错,把jvm.dll(路径:jdk1.8.0_121\jre\bin\server)注册到系统。

具体如何注册参考这篇文章:https://jingyan.baidu.com/article/fb48e8be3212766e632e147f.html

 

可以写Makefile一步到位,Makefile:

all: run
 
HelloWorld.class: HelloWorld.java
       javac HelloWorld.java

hello_world: hello_world.c
       gcc -D__int64="long long" -Ic:/java/jdk1.8.0_121/include/-Ic:/java/jdk1.8.0_121/include/win32 -o hello_world hello_world.c -Lc:/java/jdk1.8.0_121/jre/bin/server -ljvm

run: HelloWorld.class hello_world
       ./hello_world

clean:
       rm -f HelloWorld.class hello_world

 编译和运行:

>make

输出结果:

javac HelloWorld.java
gcc -Ic:/java/jdk1.8.0_121/include/ -Ic:/java/jdk1.8.0_121/include/win32 -ohello_world hello_world.c -L c:/java/jdk1.8.0_121/jre/bin/server -ljvm
./hello_world
Launched JVM! :)
Hello, World
20 squared is 400
20 raised to the 3power is 8000

 

使用适配器模式设计RMI方式的网络应用程序

 使用适配器模式设计RMI方式的网络应用程序为网络应用编写本地Java对象指南 简介:    使用Java的RMI方式编写基于网络的应用程序是非常简单的。然而,使用不是基于网络的类,而且还把它复杂化来...
  • wearebug
  • wearebug
  • 2002-04-01 09:31:00
  • 1126

C语言调用JAVA的例子

  • 2009年04月18日 13:38
  • 7KB
  • 下载

JNI Helloworld

  • 2010年03月18日 22:49
  • 1KB
  • 下载

最近看了Java 调用C 和 C/C++反调Java,感叹当年的大牛为什么要这么弄

于是自己模仿他的设计也写了个小程序,晒晒,关键就是C++包裹了一个类 struct JNIEnv_ ,内部又通过组合的方式加入了const struct JNINativeInterface_ 的指针...
  • dengxu11
  • dengxu11
  • 2011-09-05 16:00:04
  • 8331

openSSL学习例子(代码含c与java两版本)

由于工作需要,最近有空研究了一个openSSL,分别用c与java写了一个测试用例,分享给朋友,有需要的可以自行下载下来学习。说明一点:在运用本人的c版本程序,请先按本配好openssl的lib库,可...
  • u010725842
  • u010725842
  • 2016-01-18 18:39:04
  • 1255

jni C语言调用java的小例子(java返回string)

jclass regionClass = env->FindClass("com/oppo/util/RfUtils"); //查找java类RfUtils if(regi...
  • u012824494
  • u012824494
  • 2016-09-20 17:08:58
  • 1240

IntelliJ IDEA平台下JNI编程(四)—本地C代码访问JAVA对象

本文主要针对C代码中访问JVM中对象的普通变量、静态属性、普通函数、静态函数进行举例讲解,通过本文的学习将进一步理解JNIEnv在本地代码和Java之间的重要性。有了前面几篇文章的基础,学习起本文来将...
  • huachao1001
  • huachao1001
  • 2017-03-22 21:29:51
  • 1402

NDK中JAVA和C互相调用

  • 2013年04月07日 15:38
  • 496KB
  • 下载

JAVA调用C

  • 2008年01月04日 13:05
  • 3.28MB
  • 下载

C语言调用 Java(Linux)

一、书写C文件,模拟JDK中自带的java命令 [cpp] view plaincopy #include    #include    #include    int mai...
  • weiqubo
  • weiqubo
  • 2015-09-02 17:12:32
  • 2178
收藏助手
不良信息举报
您举报文章:C调用java例子
举报原因:
原因补充:

(最多只允许输入30个字)