2015-06-16 8 views
12

जेएलएस v7 के chapter 18 में व्याकरण प्रलेखन में कहीं और संरचनाओं से अलग दिखता है, लेकिन मेरे लिए भिन्नता प्रतीत होती है। विशेष रूप से अध्याय 15 में नियम हैं:क्या जावा 7 spec में व्याकरण वास्तव में बराबर है?

RelationalExpression: 
    ShiftExpression 
    RelationalExpression < ShiftExpression 
    RelationalExpression > ShiftExpression 
    RelationalExpression <= ShiftExpression 
    RelationalExpression >= ShiftExpression 
    RelationalExpression instanceof ReferenceType 

जो foo instanceof Bar एक RelationalExpression बनाता है (और इसलिए एक EqualityExpresson) जो बदले में EqualityExpression नियम जो foo instanceof Bar == false एक EqualityExpression बनाता में एलएचएस रूप में इस्तेमाल किया जा सकता है।

लेकिन जब अध्याय 18 में व्याकरण को देखकर वे यह थोड़ा आसान बना दिया है:

Expression2: 
    Expression3 [Expression2Rest] 

Expression2Rest: 
    { InfixOp Expression3 } 
    instanceof Type 

कौन सा अजीब लग रहा है, जिसका अर्थ है कि हम कर सकते हैं श्रृंखला एक साथ Expression3 द्विआधारी ऑपरेटरों या हम प्रकार की जांच कर सकते हैं साथ रों एक Expression3 का। विशेष रूप से अब foo instanceof Bar एक Expression2 है, लेकिन मुझे नहीं लगता कि यह समानता तुलना के एलएचएस के रूप में Expression2 का उपयोग करने के लिए मान्य होगा।

क्या मुझे अध्याय 18 के व्याकरण में कुछ याद आया है जो foo instanceof Bar == false को वैध अभिव्यक्ति बनाता है? ध्यान दें कि यह अध्याय 15 के नियमों और मेरे कंपाइलर के अनुसार नियमों के अनुसार एक मान्य अभिव्यक्ति है।

+4

मुझे कल्पना में एक बग की तरह लगता है। ध्यान दें कि [जावा 8 spec के समकक्ष अनुभाग] (https://docs.oracle.com/javase/specs/jls/se8/html/jls-19.html) अध्याय 15. के रूप में एक ही व्याकरण का उपयोग करता है। –

+1

क्यों होगा यह एक समस्या है कि 'foo exampleof bar == false' वैध अभिव्यक्ति है? मैंने अभी इसकी जांच की है और संकलक इसे स्वीकार करता है। – Clashsoft

+1

@Clashsoft कोई समस्या नहीं है, सिवाय इसके कि बाद के व्याकरण के अनुसार यह नहीं है: 'foo exampleof bar' एक 'अभिव्यक्ति 2' है और उसमें, लेकिन 'x == y' का एलएचएस 'अभिव्यक्ति 3' होना चाहिए। बेशक जब तक मुझे कुछ याद नहीं आया - जो (जो मैंने याद किया है) मेरे प्रश्न का उत्तर होगा। – skyking

उत्तर

2

इस प्रश्न का एक अच्छा जवाब है, तो चलो एक अच्छा नजदीक देखो।

अध्याय 18 में व्याकरण पर आधारित: एक InfixOp (जैसे ==) के साथ

कुछ भी या तो Expression2Rest फिट बैठता है या कुछ भी नहीं फिट बैठता है। और अभिव्यक्ति 2Rest केवल अभिव्यक्ति 2 के अंदर है। इसलिए, यदि foo instanceof Bar == false कानूनी जावा है, तो इसका मतलब है कि foo instanceof Bar को अभिव्यक्ति 3 होना चाहिए।

expression2:
Expression3 [Expression2Rest]

Expression2Rest:
{InfixOp Expression3}
instanceofप्रकार

लेकिन foo instanceof Barअभिव्यक्ति 3 नहीं है। PrefixOp और कोई कलाकार नहीं है, इसलिए अभिव्यक्ति 3 होने के लिए इसे प्राथमिक होना होगा। लेकिन यह बस फिट नहीं है।

Expression3:
PrefixOp Expression3
((अभिव्यक्ति | प्रकार))Expression3
प्राथमिक {चयनकर्ता} {} PostfixOp

प्राथमिक:
शाब्दिक
ParExpression
इस[तर्क]
सुपरSuperSuffix
नईप्रजापति
NonWildcardTypeArguments (ExplicitGenericInvocationSuffix | इस तर्क)
पहचानकर्ता {पहचानकर्ता} [IdentifierSuffix]
BasicType {[]} * .class
void.class

निष्कर्ष: अध्याय 18 में प्रस्तुत व्याकरण पर आधारित, foo instanceof Bar == false है कानूनी जावा अभिव्यक्ति नहीं है। !?!?!

बेशक यह बकवास है। foo instanceof Bar एक बूलियन परिणाम उत्पन्न करता है, और इसका परिणाम निश्चित रूप से false से तुलना की जा सकती है। अभिव्यक्ति संकलित और चलाता है।

बेहतर निष्कर्ष: अध्याय 18 आधिकारिक नहीं है, लेकिन शेष पुस्तक है।

धारा 2.3 राज्यों

जावा प्रोग्रामिंग भाषा के लिए एक वाक्यात्मक व्याकरण अध्याय 4, 6-10, 14 में दी गई है, और 15 ... अध्याय 18 के लिए भी एक वाक्यात्मक व्याकरण देता है कि जावा प्रोग्रामिंग भाषा, प्रदर्शनी से कार्यान्वयन के लिए बेहतर अनुकूल है।

अध्याय 15 में प्रस्तुत व्याकरण के नियमों के अनुसार, foo instanceof Bar == false एक कानूनी जावा अभिव्यक्ति है। लेकिन धारा 15.20.1 से पहले अंतिम वाक्य देखें: "एक संबंधपरक अभिव्यक्ति का प्रकार हमेशा बूलियन है।"यह सीधे RelationalExpression 15.20 में खुद को नियम के खिलाफ है (विशेष रूप से, इसका अर्थ है कि instanceof की एलएचएस बूलियन को मूल्यांकन करना चाहिए।) यह संभवतः सच नहीं हो सकता है

Bestest निष्कर्ष:।। इस किताब को समस्याएं हैं। अगर आप जानना चाहते हैं कि कुछ कानूनी जावा है, तो आपको इसे ओरेकल के संदर्भ कार्यान्वयन पर अधिमानतः चलाने और चलाने की ज़रूरत है। और फिर भी वहां बग हो सकते हैं। आखिरकार, सॉफ्टवेयर ही है।

और मुझे लगता है कि अगर उन्होंने अभिव्यक्ति 2 नियम को थोड़ा सा बदल दिया है, तो अध्याय 18 सही हो सकता है। ऐसा:

* expression2:
Expression3 [instanceofप्रकार]
expression2 {InfixOp Expression3}

लेकिन कौन जानता है, कि अन्य समस्याओं के कारण हो सकता है। किसी भी मामले में, यह जावा 8 में तय किया गया है।

संबंधित मुद्दे