原文:http://www.cnblogs.com/youxilua/archive/2011/09/16/2178554.html

1,先把c语言的编译环境搭建好,windows下这里使用mingw

1,mingw具体配置

配置环境变量: 
                         打开:“我的电脑->属性->高级->环境变量->系统变量”编辑如下系统变量: 
                         变量名                            变量值 
                         PATH                             C:\MinGW\bin; 
                         LIBRARY_PATH                C:\MinGW\lib 
                         C_INCLUDEDE_PATH        C:\MinGW\include 
                         CPLUS_INCLUDE_PATH      C:\MinGW\include\c++\3.4.2;C:\MinGW\include\c++\3.4.2\mingw32;C:\MinGW\include\c++\3.4.2\backward;C:\MinGW\include

盘符自己搞定吧…

2,开始第一个JNI

1,JNI的原理图

直接到官方教程那里截的….

2,开始使用JNI

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
package kg.tom;
 
public class MyJni {
    //使用JNI的关键字native
    //这个关键字决定我们那些方法能在我们的C文件中使用
    //只须声明,不必实现
     public native void display();
     public native double sum(double x,double y);
      
    //这个是到时候调用我们写好的C文件
    //现在用不上
    //static {
    //  System.loadLibrary("sum");
    //}
     
     
    public static void main(String[] args) {
        //到时候测试用方法现在用不上
        //new MyJni().display();
        //System.out.println(new MyJni().sum(2.0, 3.0));
    }
}

然后,就是返回到我们的java基础了…将我们写好的类,转换成头文件

1,先把写好的类转换成.class文件

2,把.class文件转换成头文件,成功的话就会在src目录下看到.h文件了

打开后你会看到

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class kg_tom_MyJni */
 
#ifndef _Included_kg_tom_MyJni
#define _Included_kg_tom_MyJni
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     kg_tom_MyJni
 * Method:    display
 * Signature: ()V
 */
JNIEXPORT void JNICALL Java_kg_tom_MyJni_display
  (JNIEnv *, jobject);
 
/*
 * Class:     kg_tom_MyJni
 * Method:    sum
 * Signature: (DD)D
 */
JNIEXPORT jdouble JNICALL Java_kg_tom_MyJni_sum
  (JNIEnv *, jobject, jdouble, jdouble);
 
#ifdef __cplusplus
}
#endif
#endif

native方法名称转换详解:

英语原文 我的理解… 例子

the prefix Java_

转换后的native方法全部以Java_为前缀 Java_kg_tom_MyJni_display

a mangled fully-qualified class name

接着以类的全名标识(包名+类名) Java_kg_tom_MyJni_display
  • an underscore (“_”) separator
以下划线为分隔符(“_”) Java_kg_tom_MyJni_display
mangled method name 最后就是方法的名称 Java_kg_tom_MyJni_display
  • for overloaded native methods, two underscores (“__”) followed by the mangled argument signature
这个理解不能:直译的话就是对已经读取过的native方法,用双下划线(“__”)标注 没找到

3,就是写我们的C文件了

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
//必须的头文件jni.h
#include <jni.h>
//导入我们需要实现的本地方法
#include "kg_tom_MyJni.h"
#include <stdio.h>
 
JNIEXPORT void JNICALL Java_kg_tom_MyJni_display
  (JNIEnv *env, jobject obj)
{
    printf("Hello World tom!!");
    return;
}
 
JNIEXPORT jdouble JNICALL Java_kg_tom_MyJni_sum
  (JNIEnv *env, jobject obj, jdouble a, jdouble b)
{
    return a + b;
}

4,windows下编译成dll文件,linux下编译成so文件.这里只说windows下的

1,java基础

找到我们的jdk文件夹,然后打开其中的include文件夹,就会看到一些头文件,看下关键的Jni.h头文件在不在,在的话,继续,不在

自行下载一个新的jdk…

2,把C文件编译成dll文件

我们这里使用mingw….你会用VC6也可以用VC6编译…

gcc -Wall -D_JNI_IMPLEMENTATION_ -Wl,--kill-at   -Id:/java/include –Id:/java/include/win32   -shared -o sum.dll java_sum_native.c

命令 简单介绍
-Wall -D_JNI_IMPLEMENTATION_ 把我们的C文件编译成dll
-Wl,--kill-at   因为mingw默认是用@来进行分隔,会导致JNI机制不能读取,所以要删掉.. 
mingw官网解释
Id:/java/include –Id:/java/include/win32   导入我们用的的jni需要的头文件…盘符,文件夹自己修改
-shared -o 输出配置,第一个参数为我们输出的名字(随便起),第二个参数为我们的C文件(随便起)
   

没出什么提示的话就是成功的了…

4,运行我们的JNI

1,用eclipse的话,我们把编译好的dll放到项目根目录,注意不是代码根目录

1
2
3
4
5
6
7
8
9
10
//把刚才注释的地方删掉..
//这就是必须的,用来读取我们写好的C语言编译好的dll,后缀是系统自己辨认…千万不要自己写
static {
        System.loadLibrary("sum");
    }
//mian方法中
//用底层c代码实现输出..呵呵~~
new MyJni().display();
//用c计算会不会快点呢..呵呵~
System.out.println(new MyJni().sum(2.0, 3.0));

输出结果

貌似java本身的输出,优先级比较高??

2,补充一下:

1,我们要运行我们编译的C文件,是与我们创建的类是必须一起存在,

例如:我把MyJni.java删掉,然后另起一个Hello.java能不能直接调用dll中的方法呢?那是肯定不行的..因为,jni需要类名来进行查找

JNI 简单例子的更多相关文章

  1. Hibernate4.2.4入门(一)——环境搭建和简单例子

    一.前言 发下牢骚,这段时间要做项目,又要学框架,搞得都没时间写笔记,但是觉得这知识学过还是要记录下.进入主题了 1.1.Hibernate简介 什么是Hibernate?Hibernate有什么用? ...

  2. AgileEAS.NET SOA 中间件平台.Net Socket通信框架-简单例子-实现简单的服务端客户端消息应答

    一.AgileEAS.NET SOA中间件Socket/Tcp框架介绍 在文章AgileEAS.NET SOA 中间件平台Socket/Tcp通信框架介绍一文之中我们对AgileEAS.NET SOA ...

  3. spring mvc(注解)上传文件的简单例子

    spring mvc(注解)上传文件的简单例子,这有几个需要注意的地方1.form的enctype=”multipart/form-data” 这个是上传文件必须的2.applicationConte ...

  4. ko 简单例子

    Knockout是在下面三个核心功能是建立起来的: 监控属性(Observables)和依赖跟踪(Dependency tracking) 声明式绑定(Declarative bindings) 模板 ...

  5. mysql定时任务简单例子

    mysql定时任务简单例子 ? 1 2 3 4 5 6 7 8 9     如果要每30秒执行以下语句:   [sql] update userinfo set endtime = now() WHE ...

  6. java socket编程开发简单例子 与 nio非阻塞通道

    基本socket编程 1.以下只是简单例子,没有用多线程处理,只能一发一收(由于scan.nextLine()线程会进入等待状态),使用时可以根据具体项目功能进行优化处理 2.以下代码使用了1.8新特 ...

  7. 一个简单例子:贫血模型or领域模型

    转:一个简单例子:贫血模型or领域模型 贫血模型 我们首先用贫血模型来实现.所谓贫血模型就是模型对象之间存在完整的关联(可能存在多余的关联),但是对象除了get和set方外外几乎就没有其它的方法,整个 ...

  8. [转] 3个学习Socket编程的简单例子:TCP Server/Client, Select

    以前都是采用ACE的编写网络应用,最近由于工作需要,需要直接只用socket接口编写CS的代码,重新学习这方面的知识,给出自己所用到的3个简单例子,都是拷贝别人的程序.如果你能完全理解这3个例子,估计 ...

  9. jsonp的简单例子

    jsonp的简单例子 index.html <!DOCTYPE html> <html> <head> <meta charset="UTF-8&q ...

随机推荐

  1. 2.2.10数据类型String的常量池特性

    在JVM中具有String常量池缓存的功能 package com.cky.test; /** * Created by edison on 2017/12/8. */ public class Te ...

  2. Write Markdown Syntax Online Document with Sphinx and Pandoc

    There is no doubt that we have to write doc while we are developing software. But How do you write d ...

  3. Java Applet在IE中浏览

    1. IE --> 工具 --> Internet选项 --> 取消“将Java1.6.0.4加入Internet”选择项. 2. 开始 --> 控制面板 --> Jav ...

  4. noip第1课资料

  5. POJ1446 Girls and Boys

    Girls and Boys Time Limit: 5000MS   Memory Limit: 10000K Total Submissions: 12747   Accepted: 5678 D ...

  6. HDU3488 Tour

    Tour Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 65535/65535 K (Java/Others) Total Submi ...

  7. Java 是值传递

    本质:传值/传地址值   以下搬运自知乎大佬   作者:Intopass链接:https://www.zhihu.com/question/31203609/answer/50992895来源:知乎著 ...

  8. SRM466

    250pt: 给出一个数n(n <= 10^10),问至少修改几位能使其变成完全平方数. 思路:     直接枚举平方根,然后统计.     注意枚举时要枚举到比她大.. #line 7 &qu ...

  9. Poj2296

    题意:给定n个点,然后在每个点在一个正方形的上边或者下边的中点,并且所有的正方形等大且不能重叠.求正方形最大的边长是多少. 思路:很明显的二分边长+判定.不过判定要用到2-sat,算是2-sat的入门 ...

  10. Spring中ApplicationEvent和ApplicationListener封装

    1.测试程序EventTest.java,发布一个事件只需要调用FrameEventHolder.publishEvent()方法即可. package com.junge.spring.event; ...