2009-11-09 37 views
19

Tôi có một đoạn mã mà tôi cần phải vượt qua lớp của một trường trong một phương thức. Bởi vì các cơ chế của mã của tôi, tôi chỉ có thể xử lý các đối tượng tham chiếu và không phải nguyên thủy. Tôi muốn một cách dễ dàng để xác định nếu một loại của Field là nguyên thủy và trao đổi nó với lớp wrapper thích hợp. Vì vậy, trong mã những gì tôi làm cho đến nay là một cái gì đó như thế này:Cách đơn giản để có được loại lớp bao bọc trong Java

Field f = getTheField(); // Dummy method that returns my Field 
Class<?> c = f.getType(); 
if (c == int.class) { 
    c = Integer.class; 
} 
else if (c == float.class) { 
    c = Float.class; 
} 
// etc 
myMethod(c); 

này hoạt động tốt, ngoại trừ một thực tế rằng tôi cần phải kiểm tra một cách rõ ràng cho tất cả các loại nguyên thủy và trao đổi chúng với lớp wrapper thích hợp. Bây giờ tôi biết rằng không có nhiều loại nguyên thủy và nó sẽ không là vấn đề đơn giản để liệt kê tất cả chúng, nhưng tôi đã tự hỏi liệu có cách nào dễ dàng hơn và thanh lịch hơn để thực hiện nó hay không.

Trả lời

33

Tôi sử dụng Thư viện Google Bộ sưu tập trong câu trả lời của mình, vì tôi đã hư hỏng như vậy, nhưng bạn có thể thấy cách thực hiện với HashMaps đơn giản nếu bạn thích.

// safe because both Long.class and long.class are of type Class<Long> 
    @SuppressWarnings("unchecked") 
    private static <T> Class<T> wrap(Class<T> c) { 
    return c.isPrimitive() ? (Class<T>) PRIMITIVES_TO_WRAPPERS.get(c) : c; 
    } 

    private static final Map<Class<?>, Class<?>> PRIMITIVES_TO_WRAPPERS 
    = new ImmutableMap.Builder<Class<?>, Class<?>>() 
     .put(boolean.class, Boolean.class) 
     .put(byte.class, Byte.class) 
     .put(char.class, Character.class) 
     .put(double.class, Double.class) 
     .put(float.class, Float.class) 
     .put(int.class, Integer.class) 
     .put(long.class, Long.class) 
     .put(short.class, Short.class) 
     .put(void.class, Void.class) 
     .build(); 

Thật kỳ quặc là không có gì tồn tại trong JDK cho điều này, nhưng thực sự không có gì.

EDIT: Tôi hoàn toàn quên rằng chúng tôi phát hành này:

http://google.github.io/guava/releases/21.0/api/docs/com/google/common/primitives/Primitives.html

Nó có phương pháp bọc(), cộng với Unwrap() và một vài điều ngẫu nhiên khác.

+0

Vì vậy, về cơ bản cùng một điều ... :) Cảm ơn câu trả lời. Về cơ bản không có cách nào khác vào lúc này. –

6

Bạn có thể gọi class.isPrimitive() để biết nếu nó là nguyên thủy hay không, tuy nhiên, không có phương thức boxing để chuyển đổi các lớp trong JDK. Có ít nhất một open bug liên quan đến điều này.

+0

Ngoài ra còn có các trường trong lớp bao bọc sẽ cho phép bạn vào các lớp nguyên thủy (ví dụ: 'Double.TYPE' là giống như 'double.class'), nhưng không có cách nào xấu xí để tận dụng lợi thế của chương trình đó. –

5

Dưới đây là một cách khác nếu bạn không cần mã tối ưu hóa cao:

Class<?> primitive=long.class; 
    Class<?> boxed=Array.get(Array.newInstance(primitive,1),0).getClass(); 
    System.out.println(primitive.getName()); 
    System.out.println(boxed.getName()); 
0

Ngoài ra còn có com.sun.beans.finder.PrimitiveWrapperMap # getType (primitiveName). Nhưng tất nhiên sử dụng các lớp học từ gói "com.sun" không thực sự được đề xuất ...

Các vấn đề liên quan