2011-02-07 34 views
14

Có thể sắp xếp một phương thức theo thứ tự? Bởi vì khi tôi nhìn vào tài liệu, lớp Method không thực hiện Serializable. Vì vậy, có bất kỳ lựa chọn thay thế?Phương pháp nối tiếp Java

+6

bạn đang cố gắng làm gì đây? Tuần tự hóa bytecode ?! – EboMike

+0

nó không phải là như vậy tôi chỉ đang cân nhắc nếu nó có thể bởi vì tôi có một câu hỏi khác nếu tôi đảm bảo nó là có thể –

+1

Điều đó vẫn không trả lời câu hỏi của tôi. Bạn đang cố gắng tuần tự hóa bytecode, tức là bạn đang cố gắng lấy toàn bộ phương thức và đặt nó vào luồng hoặc bạn chỉ đang cố gắng tuần tự hóa dữ liệu lôgíc, tức là gói, tên phương thức và loại đối số? – EboMike

Trả lời

9

Vì Phương thức không triển khai Serializable, nó không thể được tuần tự hóa bằng cách sử dụng API tuần tự hóa Java chuẩn.

Giải pháp thay thế sẽ là tự tuần tự hóa tên của lớp và phương thức và các loại tham số của nó. Sau đó, bạn có thể tạo lại cá thể Phương thức trong quá trình deserialization.

1

Nếu bạn tự hỏi, có thể không, không: nó không triển khai Serializable. Ngoài ra, Method là lớp cuối cùng, vì vậy bạn không thể phân lớp nó để thêm một số chức năng.

6

Điều đó phụ thuộc vào ý bạn. Thực sự, vì các phương tiện đã đề cập đến không thể được tuần tự hóa. Nhưng nếu bạn muốn tuần tự hóa logic mà phương thức thực hiện và (ví dụ) gửi nó qua mạng thì có thể. Việc tuần tự hóa này có thể được thực hiện bằng cách tuần tự hóa lớp. Trên thực tế .class đã là một chuỗi các byte có thể được lưu trữ (và thường được lưu trữ) trong các tệp. Bạn chỉ có thể gửi nó qua mạng nếu bạn muốn và sau đó khởi tạo bằng cách sử dụng Class.forName(). Hơn nữa, bạn có thể làm tốt hơn: sử dụng HttpClassLoader, chuyển cho nó URL HTTP nơi lớp của bạn có sẵn, tạo cá thể lớp bằng cách sử dụng trình nạp lớp này và chạy bất kỳ phương thức nào bạn muốn.

+2

gửi một lớp qua mạng phức tạp hơn gửi byte và sau đó gọi class.forname(). class.forname() chỉ tải một lớp đã có trên classpath. trước tiên bạn phải làm cho các byte đó có sẵn trên classpath bằng cách nào đó. – jtahlborn

+0

Bạn nói: "Nhưng nếu bạn muốn tuần tự hóa logic mà phương thức thực hiện và (ví dụ) gửi nó qua mạng thì có thể. Việc tuần tự hóa này có thể được thực hiện bằng cách tuần tự hóa lớp. Trên thực tế .class đã là một chuỗi các byte có thể được lưu trữ (và thường được lưu trữ) trong các tệp. " Bạn có nghĩa là tôi có thể serialize việc thực hiện các phương pháp? Nếu điều đó là có thể, Liệu có thể tuần tự hóa các phương thức được overriden thông qua các khai báo của các lớp ẩn danh không? –

0

Thought Works thư viện xStream thực hiện điều đó rất tốt. Đây là hai phút tutorial.

+0

Xin lỗi, không có gì về việc serializing 'Methods' trong đó –

+1

Chỉ cần truyền một thể hiện Method tới x serial XML xStream và bạn sẽ nhận được serialization. –

0

Python cho phép pickling phương pháp cấp cao nhất, trong Java cách gọi phương thức trên máy chủ khác là thông qua một số loại cơ chế RMI. Lớp bytecode có thể được gửi qua dây và cho tất cả các phụ thuộc được thỏa mãn - sử dụng URLClassloader để thực hiện việc này.

1

Thực ra, tất cả các phương pháp đều là một phần của lớp học và Classkhông triển khai Serializable. Vì bạn sẽ cần một đối tượng của lớp để gọi phương thức, bạn chỉ có thể gửi lớp (hoặc đối tượng).

Tuy nhiên, ở bên nhận, thường sẽ có đối tượng phiên bản của lớp ở đó.

Nếu bạn muốn sử dụng phương pháp này để gọi phương thức ở phía xa, hãy xem RMI (gói java.rmi.*) - nó cũng hỗ trợ gửi các đối tượng khi phía từ xa chưa có dữ liệu lớp.

4

bạn có thể sử dụng các wrapper sau để cho phép phương pháp serialiation:

public class SerializableMethod implements Serializable 
{ 
    private static final long serialVersionUID = 6631604036553063657L; 
    private Method method; 

    public SerializableMethod(Method method) 
    { 
     this.method = method; 
    } 

    public Method getMethod() 
    { 
     return method; 
    } 

    private void writeObject(ObjectOutputStream out) throws IOException 
    { 
     out.writeObject(method.getDeclaringClass()); 
     out.writeUTF(method.getName()); 
     out.writeObject(method.getParameterTypes()); 
    } 

    private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundException 
    { 
     Class<?> declaringClass = (Class<?>)in.readObject(); 
     String methodName = in.readUTF(); 
     Class<?>[] parameterTypes = (Class<?>[])in.readObject(); 
     try 
     { 
      method = declaringClass.getMethod(methodName, parameterTypes); 
     } 
     catch (Exception e) 
     { 
      throw new IOException(String.format("Error occurred resolving deserialized method '%s.%s'", declaringClass.getSimpleName(), methodName), e); 
     } 
    } 
} 
Các vấn đề liên quan