Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Java

วิธาสร้าง Instance ของ VarHandle ใน Java 9

โดยทั่วไป Variable Handle คือ typed reference ไปยัง variable จะเป็น array element, instance field หรือ static field ของคลาส VarHandle class ให้ write และ read access ตัวแภภายใต้เงื่อนไขเฉพาะ เหล่านี้เป็น immutable และไม่มี visible state ไม่สามารถ sub-class ได้ แต่ละ VarHandle มี generic type T ซึ่งเป็น type ของแต่ละ variable ที่แทน จุดประสงค์ของ VarHandle คือกำหนด standard สำหรับเรียก equivalents ของ java.util.concurrent.atomic และ sun.misc.Unsafe operations บน fields และ array elements

ตัวอย่าง: ใช้ MethodHandles.lookup()


import java.lang.invoke.VarHandle;
import java.lang.invoke.MethodHandles;

public class VarHandleInstanceTest {
    public static void main(String args[]) {
        try {
            VarHandle fieldHandle = MethodHandles.lookup()
                .in(Student.class)
                .findVarHandle(Student.class, "studentId", int.class);
            
            System.out.println("VarHandle instance created successfully!!!");
        } catch (NoSuchFieldException | IllegalAccessException e) {
            e.printStackTrace();
        }
    }
}

// Student class
class Student {
    protected int studentId;
    private String[] marks;
    
    public Student() {
        studentId = 0;
        marks = new String[] {"75", "85", "95"};
    }
}

ผลลัพธ์


VarHandle instance created successfully!!!

คำอธิบาย

  • MethodHandles.lookup() - ได้ Lookup object สำหรับ caller class
  • .in(Student.class) - เปลี่ยน lookup context ไปที่ Student class (เข้าถึง protected/private ได้)
  • .findVarHandle(Student.class, "studentId", int.class) - หา VarHandle สำหรับ instance field
  • Parameters: declaring class, field name, field type

VarHandle Factory Methods

Method Use Case Parameters
findVarHandle Instance field (declaringClass, fieldName, fieldType)
findStaticVarHandle Static field (declaringClass, fieldName, fieldType)
arrayElementVarHandle Array elements (arrayClass) - e.g., int[].class
byteBufferViewVarHandle ByteBuffer view (byteOrder, fieldType)

VarHandle Usage Examples


// Instance field access
VarHandle vh = MethodHandles.lookup()
    .in(Student.class)
    .findVarHandle(Student.class, "studentId", int.class);

Student s = new Student();
vh.get(s);                    // Read: 0
vh.set(s, 123);               // Write
vh.getAndAdd(s, 10);          // Atomic add: 123 -> 133
vh.compareAndSet(s, 133, 200); // CAS: true, value=200

// Array access
VarHandle arrVh = MethodHandles.arrayElementVarHandle(int[].class);
int[] arr = new int[10];
arrVh.set(arr, 5, 100);       // arr[5] = 100
arrVh.getAndAdd(arr, 5, 50);  // arr[5] = 150, returns 100

// Static field access
VarHandle staticVh = MethodHandles.lookup()
    .in(MyClass.class)
    .findStaticVarHandle(MyClass.class, "count", int.class);
staticVh.get();               // Read static field
staticVh.getAndIncrement();   // Atomic increment

Access Mode Requirements

Access Mode Field Modifier Required
Plain None
Volatile volatile
Acquire/Release volatile
Opaque volatile
Compare-and-Set volatile

ข้อดีของ VarHandle

  • Type-safe - generic type parameter
  • Standard API - ไม่ต้องใช้ Unsafe
  • Flexible - รองรับทุก access modes
  • Composable - ทำงานกับ MethodHandles
  • JIT optimized - JVM รู้จัก pattern นี้ดี