2010-08-04 26 views
10

मेरे पास जेपीए में तारों के लिए मैप किए गए स्कैला में एक गणना है। अधिक आरामदायक कोडिंग के लिए, मैंने उनके बीच निहित रूपांतरण परिभाषित किया। तो अब मैं मूल्य val person.role = "User" परिभाषित कर सकता हूं, - person.role गणना प्रकार एक स्ट्रिंग है इसलिए रूपांतरण है। लेकिन जब मैं इन दोनों की तुलना करने की कोशिश करता हूं, तो मुझे हमेशा झूठा लगता है, क्योंकि def equals (arg0: Any) : BooleanAny लेता है इसलिए कोई रूपांतरण ट्रिगर नहीं होता है। मुझे कुछ स्पष्ट रूपांतरण की ज़रूरत है, लेकिन मेरी योजना को छोड़ने में सक्षम होना था, आपको क्या लगता है कि सबसे अच्छा अभ्यास है यहाँ सबसे साफ समाधान?स्ट्रिंग और गणना की तुलना

+0

क्या आप इस गणना को 'गणना' और 'मूल्य' पर आधारित कर रहे हैं? – Thomas

+0

@ थॉमस हां मैं स्कैला के 'स्काला' एनीमेशन 'और' स्कैला 'का उपयोग कर रहा हूं। गणना। वैल्यू – coubeatczech

+0

तुलना के लिए संदर्भ/उपयोग केस क्या है? पैटर्न मिलान एक बेहतर समाधान प्रदान कर सकता है, लेकिन यह वास्तव में उस पर निर्भर करता है जो आप पूरा करने की कोशिश कर रहे हैं। –

उत्तर

16

Value("User") आपके Enumeration में Val प्रकार का है। और मेरा मानना ​​है कि यह equals का कार्यान्वयन मूल्य के स्ट्रिंग नाम की तुलना नहीं करता है। मुझे लगता है कि ऐसा करने का एक भारी हाथ तरीका अपना खुद का Enumeration और Val बना रहा है ताकि नाम मिलान होने पर यह सच हो जाए।

लेकिन मेरे कोड में, जेपीए के साथ नहीं, मैं हमेशा स्ट्रिंग को MyEnumeration.Value में परिवर्तित करता हूं।

object E extends Enumeration { val User = Value("User") } 

scala> val a = E.withName("User") 
a: E.Value = User 

नोट जब withName का उपयोग कर, अगर स्ट्रिंग गणन में किसी भी नाम से मेल नहीं खाता है कि आप एक अपवाद प्राप्त: इस तरह की बातें करना आसान है।

तो हमेशा अपने तुलना में शुमार क्षेत्रों का उपयोग करें:

scala> a == E.User 
res9: Boolean = true 

जेपीए केवल एक स्ट्रिंग देता है, और वहाँ उसके चारों ओर कोई रास्ता नहीं है। तो मुझे लगता है कि सबसे अच्छा विकल्प या तो स्ट्रिंग को स्ट्रिंग और मिलान स्ट्रिंग में कनवर्ट करना है, या स्ट्रिंग को वैल में अपग्रेड करना और वैल की तुलना करना है। इन प्रकारों को मिलाकर तुलना के लिए काम नहीं करेगा, जब तक कि आप equals विधि में किसी प्रकार का एक्सटेंशन लागू नहीं करते हैं, और यह मुश्किल है।

13

, थॉमस के जवाब में विस्तार करते हुए आप शाखा की तुलना उपयोग कर रहे हैं, पैटर्न मिलान का उपयोग कर अधिक उपयुक्त हो सकता:

object Role extends Enumeration { 
    val User = MyValue("User") 
    val Admin = MyValue("Admin") 

    def MyValue(name: String): Value with Matching = 
     new Val(nextId, name) with Matching 

    // enables matching against all Role.Values 
    def unapply(s: String): Option[Value] = 
     values.find(s == _.toString) 

    trait Matching { 
     // enables matching against a particular Role.Value 
     def unapply(s: String): Boolean = 
      (s == toString) 
    } 
} 

फिर आप के रूप में उपयोग कर सकते हैं इस प्रकार है:

def allowAccess(role: String): Boolean = role match { 
    case Role.Admin() => true 
    case Role.User() => false 
    case _ => throw ... 
} 

या

// str is a String 
str match { 
    case Role(role) => // role is a Role.Value 
    case Realm(realm) => // realm is a Realm.Value 
    ... 
} 
संबंधित मुद्दे