2009-06-21 14 views
16

हम जब तक हम उदाहरण के लिए सटीक सदस्य पथ के एक शाब्दिक बयान है रन टाइम में एक वस्तु में एक मूल्य के मूल्यांकन करने की जरूरत: myobject.firstMember.secondMember [3] .text
हमने सोचा रेगेक्स का उपयोग करके इस पाठ विवरण को पार्स करने और फिर प्रतिबिंब का उपयोग करके टेक्स्ट वैल्यू का मूल्यांकन करने के लिए, लेकिन इससे पहले कि हम ऐसा करते हैं, मुझे आश्चर्य है कि क्या सी # किसी प्रकार का eval क्षमता का समर्थन करता है? इसलिए हमें खुद को पार्सिंग नहीं करना पड़ेगा। माइक्रोसॉफ्ट यह कैसे अपनी तात्कालिक खिड़की या खिड़कियों को देखते हैं?सी # eval() समर्थन

धन्यवाद बहुत बहुत,

आदि बरदा

उत्तर

12

शायद सबसे आसान तरीका है System.Web.UI से DataBinder.Eval उपयोग करने के लिए है:

var foo = new Foo() { Bar = new Bar() { Value = "Value" } }; 
var value = DataBinder.Eval(foo, "Bar.Value"); 
0

AFAIK वहाँ ऐसी कोई अंतर्निहित Eval कार्य है। आपको Regex + प्रतिबिंब तरीका जाना होगा। मुझे यह भी लगता है कि विजुअल स्टूडियो वही कर रहा है।

8

भविष्य में (5.0 समय सीमा के आसपास), "सेवा के रूप में संकलक" ऐसा करने में सक्षम हो सकता है। असल में, आप अब "मोनो" (CsharpRepl और Mono.CSharp देखें) के साथ बहुत कुछ करने में सक्षम हो सकते हैं - हालांकि, मुझे उम्मीद है कि Evaluate में स्थानीय चर आदि का उपयोग करने में सक्षम होने के संदर्भ में मुझे इसके बारे में बहुत कुछ पता होना चाहिए। - लेकिन वर्तमान एमएस .NET पेशकश में इसके लिए कोई समर्थन नहीं है।

अभी के लिए, आपको कुछ ऐसा करना होगा जैसे डेटा-बाध्यकारी कोड बहुत कुछ करता है ... इसे टोकन द्वारा अलग करें जैसे "।" और प्रतिबिंब का उपयोग करें। कड़ाई से बोलते हुए, बाइंडिंग कोड वास्तव में सीधे प्रतिबिंब के बजाय TypeDescriptor/PropertyDescriptor का उपयोग करता है, लेकिन प्रभाव वही है।

1

हालांकि कुछ हद तक भारी वजन दृष्टिकोण, आप एक नई नई असेंबली उत्सर्जित करने के लिए सी # कोडडॉम का उपयोग कर सकते हैं जिसमें कोड की उस पंक्ति के साथ एक विधि शामिल है।

यह कुछ अन्य सुझावों की तुलना में अधिक भारी हाथ है, मैं स्वीकार करता हूं, लेकिन दूसरी ओर आप सी # पार्सर को भारी उठाने देते हैं, इसलिए यह आपके द्वारा जो भी फेंक दिया जाता है उसे संभालने में सक्षम होना चाहिए क्योंकि यह वैध सी # है।

यदि आप उस मार्ग पर जाते हैं, तो आपको यह सुनिश्चित करने की भी आवश्यकता है कि आप उत्सर्जित असेंबली को फिर से उतार सकें, इसलिए AppDomains को बनाना और उतारना आवश्यक हो सकता है।

मैंने सफलतापूर्वक कार्यान्वित किया है और उपरोक्त तकनीक का उपयोग किया है। दूसरी ओर, आप उपयोग कर सकते हैं अगर एक DynamicMethod यह भी बहुत कुछ होगा हल्के वजन। हालांकि, मुझे लगता है कि दृष्टिकोण की कोशिश कभी नहीं की है, इसलिए मैं यह नहीं कह सकते कि आप सी # शाब्दिक का उपयोग कर एक DynamicMethod के शरीर को लागू कर सकते हैं या नहीं।

0

यहाँ समान मैं गतिशील नेस्ट गुण .. आप indexers के लिए addthe तर्क करने की जरूरत है उसे ढूंढने के लिए उपयोग कर रहा हूँ कुछ है ... और कुछ अतिरिक्त जाँच ... मैं अपने बुला विधि में nulls/त्रुटियों को पकड़ने कर रहा हूँ ..

 
    public static object FindDottedProperty(this object input, string propertyName) 
    { 
    if (input == null) 
     return null; 

    if (string.IsNullOrEmpty(propertyName)) 
     return null; 

    Queue props = new Queue(propertyName.Split('.')); 
    if (props.Count == 0) return null; 

    //start with input object and roll out property stack from there. 
    object ret = input; 
    while (props.Count > 0) 
    { 
     var prop = props.Dequeue(); 
     if (string.IsNullOrEmpty(prop)) return null; 

     /*** ADD INDEXER LOGIC HERE ***/ 

     //get the property's value based on the current named item 
     ret = ret.GetType().GetProperty(prop).GetValue(ret, null); 

     if (null.Equals(ret)) return null; 
    } 

    //return looked up value 
    return ret; 
    } 
1

वास्तव में, विंडोज वर्कफ़्लो फाउंडेशन की अभिव्यक्ति मूल्यांकन और नियम इंजन सुविधा इस तरह की चीजें कर सकती है। Introduction to the Windows Workflow Foundation Rules Engine देखें।

इन घटकों के बारे में एक दिलचस्प बात यह है कि उन्हें डिज़ाइन किया गया था ताकि आप अपने स्वयं के अनुप्रयोगों में डिज़ाइन-टाइम घटकों को अपने स्वयं के कस्टम वर्गों के संदर्भ में संचालित नियमों और/या अभिव्यक्तियों के सेट तैयार करने के लिए होस्ट कर सकें। उदाहरण के लिए, यदि आप "myObject" के खिलाफ एक अभिव्यक्ति डिजाइन करने के लिए यह बताना चाहते हैं, और यह पता होगा एक firstMember जो एक secondMember जो एक इंडेक्सर एक प्रकार एक पाठ संपत्ति है कि उपज है है यह है कि। आप XML के रूप में भाव और नियमों बच सकते हैं, और उन्हें रनटाइम पर वापस पढ़ें, कार्यावधि में डिजाइनर का उपयोग करने की जरूरत के बिना।

विशेष रूप से, External RuleSet Toolkit Sample देखें।

1

तुम हमेशा मेरी हल्के वजन सी # Eval कार्यक्रम की कोशिश कर सकते हैं। यह गतिशील तरीकों से सी # भाषा का एक बड़ा सबसेट संकलित करता है। मेरी वेबसाइट KamimuCode.Com

2

दुर्भाग्य से, सी # में जो कुछ भी आप पूछ रहे हैं उसके लिए कोई मूल सुविधाएं नहीं हैं।

हालांकि, मेरा सी # eval प्रोग्राम सी # कोड का मूल्यांकन करने की अनुमति देता है। यह रनटाइम पर सी # कोड का मूल्यांकन करने के लिए प्रदान करता है और कई सी # कथन का समर्थन करता है, जिसमें "myobject.firstMember.secondMember [3] .text" जैसे अभिव्यक्ति शामिल हैं। वास्तव में, यह कोड किसी भी .NET प्रोजेक्ट के भीतर प्रयोग योग्य है, हालांकि, यह सी # सिंटैक्स का उपयोग करने तक ही सीमित है। अतिरिक्त जानकारी के लिए, मेरी वेबसाइट, http://csharp-eval.com पर एक नज़र डालें।

14

मैंने ओपन सोर्स प्रोजेक्ट, Dynamic Expresso लिखा है, जो प्रतिनिधियों (या अभिव्यक्ति वृक्ष) में सी # सिंटैक्स का उपयोग करके लिखी गई पाठ अभिव्यक्ति को परिवर्तित कर सकता है। अभिव्यक्तियों को संकुचित या प्रतिबिंबित किए बिना Expression Trees में पार्स किया गया है और बदल दिया गया है।

var interpreter = new Interpreter(); 
var result = interpreter.Eval("8/2 + 2"); 

या

var interpreter = new Interpreter() 
       .SetVariable("service", new ServiceExample()); 

string expression = "x > 4 ? service.SomeMethod() : service.AnotherMethod()"; 

Lambda parsedExpression = interpreter.Parse(expression, 
         new Parameter("x", typeof(int))); 

parsedExpression.Invoke(5); 

मेरा काम स्कॉट गु लेख http://weblogs.asp.net/scottgu/archive/2008/01/07/dynamic-linq-part-1-using-the-linq-dynamic-query-library.aspx पर आधारित है:

आप की तरह कुछ लिख सकते हैं।

+1

यह बहुत ही रोचक है। मैंने इसे आपके वेब डेमो पर करने की कोशिश की लेकिन त्रुटि "अभिव्यक्ति अपेक्षित" मिली: [1,2,3] .Sum() – ShitalShah

+0

@ShitalShah Array घोषणा समर्थित नहीं है। आप किसी फ़ंक्शन या पैरामीटर/चर से बनाए गए सरणी पर Sum को कॉल कर सकते हैं। –

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