जहां तक जावाडोक MethodHandles.lookup()
रिटर्न सुविधा है जिसमें इस फ़ंक्शन के कॉलर के समान विधि/फ़ंक्शंस/कन्स्ट्रक्टर तक पहुंचने की क्षमता है। विशेष रूप से, यदि कॉलर कुछ निजी डेटा तक पहुंच सकता है, तो इस विधिHandles.Lookup सुविधा के रूप में। नीचे दिया गया कोड दर्शाता है कि यह झूठा है। मुझे यह गलत कहां मिलती है?मेथडहैंडल लुकअप सुविधा
public class MethodHandlerAccessTest {
private static class NestedClass {
private static void foo(){}
}
@Test
public void testPrivateAccess() throws Throwable {
NestedClass.foo(); //compiles and executes perfectly
MethodType type = MethodType.methodType(void.class);
MethodHandles.Lookup lookup = MethodHandles.lookup();
MethodHandle mh = lookup.findStatic(NestedClass.class, "foo", type);
}
}
संपादित करें:
यह मैं क्या मिलता है:
java.lang.IllegalAccessException:, MethodHandlerAccessTest $ NestedClass.foo() शून्य MethodHandlerAccessTest से: सदस्य निजी है java.lang.invoke.MemberName.makeAccessException (memberName.java:507) java.lang.invoke.MethodHandles $ L पर ookup.checkAccess (MethodHandles.java:1182) java.lang.invoke.MethodHandles $ Lookup.checkMethod (MethodHandles.java:1162) java.lang.invoke.MethodHandles $ Lookup.accessStatic पर (MethodHandles.java पर: 591) java.lang.invoke.MethodHandles $ Lookup.findStatic (MethodHandles.java:587) MethodHandlerAccessTest.testPrivateAccess (MethodHandlerAccessTest.java:19 पर) sun.reflect.NativeMethodAccessorImpl.invoke0 (मूल निवासी विधि पर ) पर पर sun.reflect.NativeMethodAccessorImpl.invoke (NativeMethodAccessorImpl.java:57) sun.reflect.DelegatingMethodAccessorImpl.invoke (DelegatingMethodAccessorImpl.java:43) पर java.lang.reflect.Method.invoke (method.java:601) org.junit.runners.model.FrameworkMethod $ 1.runReflectiveCall (FrameworkMethod.java:47) org.junit.internal.runners पर। model.ReflectiveCallable.run (ReflectiveCallable.java:12) org.junit.runners.model.FrameworkMethod.invokeExplosively (FrameworkMethod.java:44) पर org.junit.internal.runners.statements.InvokeMethod.evaluate पर (InvokeMethod.java:17) org.junit.runners पर org.junit.runners.ParentRunner.runLeaf (ParentRunner.java:271) org.junit.runners.BlockJUnit4ClassRunner.runChild (BlockJUnit4ClassRunner.java:70 पर) पर .BlockJUnit4ClassRunner.runChild (BlockJUnit4ClassRunner.java:50) org.junit.runners.ParentRunner $ 3.run (ParentRunner.java3838) org.junit.runners.ParentRunner $ 1.schedule (ParentRunner.java:63) org.junit.runners.ParentRunner.runChildren ( org.junit.runners.ParentRunner.access $ 000 (ParentRunner.java:53) org.junit.runners.ParentRunner $ 2. मूल्यांकन (ParentRunner.java229) org.junit पर। runners.ParentRunner.run org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run (JUnit4TestReference.java:50) पर (ParentRunner.java:309) org.eclipse.jdt.internal.junit.runner पर .TestExecution.run (TestExecution.java:38) org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests (Remo teTestRunner.java:467) org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests (RemoteTestRunner.java:683) पर org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run पर (RemoteTestRunner.java:390) org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main (RemoteTestRunner।जावा: 197)
आपकी व्याख्या के लिए धन्यवाद। मैंने सिंथेटिक फ़ील्ड/विधियों * के बारे में कहीं और सुना, लेकिन मैंने कभी इसके साथ कभी सामना नहीं किया। क्यों MethodHandle इस व्यवहार का अनुकरण नहीं किया? लुकअप के जावाडॉक() विधि 'कॉलर पर एक लुकअप ऑब्जेक्ट देता है, जिसमें कॉलर के पास किसी भी विधि हैंडल तक पहुंचने की क्षमता है, जिसमें निजी फ़ील्ड और विधियों के लिए सीधे विधि हैंडल शामिल हैं। यह लुकअप ऑब्जेक्ट एक क्षमता है जिसे विश्वसनीय एजेंटों को सौंप दिया जा सकता है। मुझे ऐसा करने की उम्मीद है। – alexsmail
@alexsmail: संकलक सिंथेटिक विधि को कार्यान्वित कर सकता है हालांकि यह चुनता है। मैं चाहता हूं कि जेआरई एक ही काम करने की कोशिश न करे। * भाषा * आपको क्या करने की अनुमति देता है, और * बाइटकोड * आपको क्या करने की अनुमति देता है, इसके बीच अंतर करना महत्वपूर्ण है। जहां तक वीएम का संबंध है, आप 'foo() 'को कॉल नहीं कर रहे हैं, और आपके पास ऐसा करने की पहुंच नहीं है। भाषा आपको अतिरिक्त विधि जोड़कर ऐसा करने के लिए "विशेष" अधिकार देने में सक्षम है - लेकिन यह सिर्फ एक भाषा चिंता है। कॉलर (बाहरी वर्ग) वास्तव में * वीएम के परिप्रेक्ष्य से 'foo()' तक पहुंच नहीं है। –