JavaRush /Java Blog /Random-TW /反射 API。getModifiers() 方法在 Class 類別中如何運作
Георгий
等級 22
Санкт-Петербург

反射 API。getModifiers() 方法在 Class 類別中如何運作

在 Random-TW 群組發布
public native int getModifiers()類別中的 方法Class和類別中的某些常數如何相關Modifier反射 API。 getModifiers() 方法在 Class - 1 中的工作原理假設我們有一堂課:
public static abstract class NestedClass{
}
此方法getModifiers()以數位形式傳回結果,其中呼叫該方法的類別或方法的存取修飾符已加密。要呼叫getModifiers()一個類,例如 for ,您需要為該類NestedClass建立一個類物件。並打電話。 ClassNestedClassClass<NestedClass>getModifiers()
Class<NestedClass> c = NestedClass.class;
int classModifiers = c.getModifiers();
或在一行中顯示結果及其二進位表示形式:
int classModifiers = NestedClass.class.getModifiers();
System.out.printf("classModifier = %d%n",classModifiers);
System.out.printf("classModifier в двоичной системе счисления = %s%n",Integer.toBinaryString(classModifiers));
螢幕上:

classModifiers = 1033
classModifiers в двоичной системе счисления = 10000001001
好的,但是為什麼是這個特定的數字呢?我們來看一下類別的例子NestedClass。假設我們有一個方法:
public static boolean isModifierSet(int allModifiers, int specificModifier) {
}
其參數將包括: int allModifiers = NestedClass.class.getModifiers(),如上例所示。Aint specificModifier將等於類常數之一Modifier:等Modifier.PUBLICModifier.STATIC(我們將在下面考慮其餘的常數)。true如果該類別包含傳遞給 的存取修飾符,則該方法將傳回給我們specificModifier。如果不 - false。測試類別中的程式碼將如下所示:
boolean isPublic = isModifierSet(classModifiers, Modifier.PUBLIC);
boolean isInterface = isModifierSet(classModifiers, Modifier.INTERFACE);
boolean isAbstract = isModifierSet(classModifiers, Modifier.ABSTRACT);

System.out.printf("\"Is NestedClass public?\" - %b%n", isPublic); //true
System.out.printf("\"Is NestedClass interface?\" - %b%n", isInterface); //false
System.out.printf("\"Is NestedClass abstract?\" - %b%n", isAbstract); //true
如何實作該方法的邏輯isModifierSet?讓我們用二進位表示類別中的修飾符Modifier:(例如Modifier.FINAL= 0x00000010,或在 10 進位中 - 16。二進位中的 16 = 00010000)
  • Modifier.PUBLIC = 1 = 0000 0001
  • Modifier.PRIVATE= 2 = 0000 0010
  • Modifier.PROTECTED= 4 = 0000 0100
  • Modifier.STATIC= 8 = 0000 1000
  • Modifier.FINAL= 16 = 0001 0000
  • Modifier.SYNCHRONIZED= 32 = 0010 0000
  • Modifier.VOLATILE= 64 = 0100 0000
  • Modifier.TRANSIENT= 128 = 1000 0000
  • Modifier.NATIVE= 256 = 1 0000 0000
  • Modifier.INTERFACE= 512 = 10 0000 0000
  • Modifier.ABSTRACT = 1024 = 100 0000 0000
  • NestedClass.class.getModifiers()= 1033 = 100 0000 1001
我們看到了什麼?對於每個修飾符,在第 10 個修飾符中取一個數字,以便在第 2 個修飾符中,它們的 1 會向左移動一位。它getModifiers()的計算方式是,如果一個類別包含某個存取修飾符,那麼與該存取修飾符中相同的位元就等於 1。在NestedClass以下存取修飾符中:public static abstract。1PUBLIC等於 0 數字(最右)。B STATIC- 3。B ABSTRACT- 10。現在我們看看我們的NestedClass.class.getModifiers():在 0、3 和 10 數字中,它有 1!其餘的全部為零。接下來我們繼續解決問題。我們需要了解我們的getModifiers()特定修飾符是否包含。讓我們考慮一下修飾符的情況finalModifier.FINAL= 16 = 0001 0000,所以 1 等於第 4 位數字。類比上面的例子,我們看看我們的是否NestedClass.class.getModifiers()= 100 0000 1001 Modifier.FINAL。這裡第 4 位數字等於 0。這表示它不包含,這是 true ( NestedClassnot final)。但是方法中該寫什麼邏輯呢?我們需要應用一個邏輯值AND (&),如果兩個位元都為 1,則為 1。否則為 0。我們的方法最終將如下所示:
public static boolean isModifierSet(int allModifiers, int specificModifier) {
        return (allModifiers & specificModifier) > 0;
    }
讓我們確保程式碼可以工作並展示它為什麼可以工作。我們計算NestedClass.class.getModifiers() & Modifier.FINAL
  • 100 0000 1001 -NestedClass.class.getModifiers()
  • 000 0001 0000 - Modifier.FINAL(為方便起見,在左側增加了 3 個零)
  • 000 0000 0000 - 回答 0。我們沒有一個單位,因為 只有 1 & 1 = 1。1 & 0 = 0, 0 & 1 = 0, 0 & 0 = 0;
這意味著我們的表達式return將返回false,因為 0 > 0 - false. 這意味著不存在這樣的存取修飾符。我們看看吧Modifier.ABSTRACT & NestedClass.class.getModifiers()
  • 100 0000 0000 -Modifier.ABSTRACT
  • 100 0000 1001 -NestedClass.class.getModifiers()
  • 100 0000 0000 - 最左邊的單位匹配。轉換為第 10 次:答案是 1024。
這意味著我們的表達式return將返回true,因為 1024 > 0 - true. 於是就有了這樣一個訪問修飾符。 反射 API。 getModifiers() 方法在 Class - 2 中的工作原理同樣,此方法既可以應用於類別方法,也可以應用於類別欄位。該欄位的程式碼如下所示:
import java.lang.reflect.Field;
import java.lang.reflect.Modifier;

public class A {
    private static transient volatile String name = "Bob";

    public static void main(String[] args) throws NoSuchFieldException {

        Field field = A.class.getDeclaredField("name");
        int fieldModifiers = field.getModifiers();

        boolean isPublic = isModifierSet(fieldModifiers, Modifier.PUBLIC);
        boolean isFinal = isModifierSet(fieldModifiers, Modifier.FINAL);
        boolean isVolatile = isModifierSet(fieldModifiers, Modifier.VOLATILE);

        System.out.printf("\"Is A.name public?\" - %b%n", isPublic); //false
        System.out.printf("\"Is A.name final?\" - %b%n", isFinal); //false
        System.out.printf("\"Is A.name volatile?\" - %b%n", isVolatile); //true
    }
    public static boolean isModifierSet(int allModifiers, int specificModifier) {
        return (allModifiers & specificModifier) > 0;
    }
}
留言
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION