2013-02-21 42 views
6

Tôi cần gọi hàm thư viện DLL bên ngoài từ mã Java. Tôi sử dụng Netbeans 7.2. Chức năng của dll của tôi là:Cách gọi hàm dll ngoài từ mã java

Boolean isValid(string word) 
List<String> getWords(String word) 

Tôi đang theo dõi this ví dụ. Nhưng tôi không biết làm thế nào khai báo các chức năng dll của tôi. Và tôi đã tìm thấy một số khác link. Nhưng nó không hiệu quả với tôi.

+6

"Nó không hoạt động đối với tôi" không phải là * gần * đủ thông tin để chúng tôi trợ giúp bạn. Bạn cần cho chúng tôi biết những gì bạn đã thử và kết quả là gì. Vui lòng đọc http://tinyurl.com/so-list –

+0

Điều gì không hiệu quả?Bạn có thể chia sẻ một số mã của những gì bạn đã thử không? –

+0

Đối với Linux: http://stackoverflow.com/a/30635871/895245 –

Trả lời

2

Bạn sẽ cần phải sử dụng Java Native Interface (JNI), mà là một tập hợp của C C++ chức năng/cho phép mã nguồn gốc để giao tiếp với mã java (ví dụ: nhận các thông số từ các cuộc gọi chức năng java, trả kết quả, vv). Viết một thư viện C bao bọc để nhận các cuộc gọi JNI và sau đó gọi thư viện bên ngoài của bạn.

Ví dụ, hàm sau gọi một phương thức updateHandlers trên đối tượng gốc (được lưu trữ ở phía Java).

class MyImpl { 
    void updateHandlers(JNIEnv *env) { 
    this->contentHandler = ....; 
    } 
} 

JNIEXPORT void JNICALL Java_package_Classname_updateHandlers0 
    (JNIEnv *env, jobject obj, jlong ptr) 
{ 
    ((MyImpl*)ptr)->updateHandlers(env); 
} 

Các tờ khai tương ứng trong package.ClassName là:

private long ptr; //assigned from JNI 
public void updateHandlers() { 
    if (ptr==0) throw new NullPointerException(); 
    updateHandlers0(ptr); 
} 
private native void updateHandlers0(long ptr); 

static { 
    try { 
      /*try preloading the library external.dll*/ 
     System.loadLibrary("external"); 
    } catch (UnsatisfiedLinkError e) { 
     /*library will be resolved when loading myjni*/ 
    } 
    System.loadLibrary("myjni"); //load myjni.dll 
} 
1

Bạn khai báo chức năng gốc của mình trong java (native private ...) với chữ ký mà bạn cần; sau đó chạy javah (một công cụ được cung cấp với JDK) để tạo các tiêu đề gốc. A List<String> (trên thực tế là List, vì loại tẩy xoá) là jobject bằng mã gốc.

Phương pháp C tương ứng, sẽ là:

JNIEXPORT jobject JNICALL package_Classname_getWords(JNIEnv *env, jobject jobj, jstring word) 

Tôi nghĩ rằng nó sẽ được dễ dàng hơn để trả lại một mảng các chuỗi jobjectArray, và nhanh chóng Danh sách trong java từ các giá trị trả lại. Xem this example.

6

Tôi tình cờ gặp cùng một vấn đề về "gọi DLL từ Java" và trước hết là thất vọng về sự phức tạp. Tuy nhiên, có một giải pháp thanh lịch (cũng có thể là thú vị cho những người ở đó trong môi trường sống processing.org ..) Với hình thức "chung chung" của câu hỏi (có thể, giảm bớt không được biện minh cho điều đó), tôi giả sử , một giải pháp khá dễ dàng sẽ được chỉ định. Nói cách khác, một giải pháp tránh được sự lộn xộn aronud với các tập tin tiêu đề, chuyển đổi thêm, vv, cũng giống như mã nguồn không nhất thiết phải có sẵn.

Đề xuất của tôi cho điều đó sẽ là JNA (https://github.com/twall/jna), về cơ bản là một trình bao bọc đơn giản xung quanh JNI. Nó hoạt động rất tốt, việc ánh xạ kiểu đơn giản (ví dụ: pchar = lpcstr buffer -> string), mặc dù tôi chỉ sử dụng nó đối với các tệp DLL Windows và các tệp DLL kiểu C của riêng tôi được tạo bằng Delphi-Pascal. Điều duy nhất cần xem xét là các giá trị trả về phải được xuất qua các hàm thay vì các biến tham chiếu được gắn cờ "out". Câu hỏi đã trỏ đến một nguồn được liên kết cung cấp một ví dụ cho điều đó (vì vậy, các câu trả lời xung quanh JNI có thể bị thất lạc ở đây). Lưu ý rằng liên kết mà tôi cung cấp cũng chứa các trục cho việc truyền mảng và con trỏ.