2009-02-23 18 views
27

मैं कक्षाओं का एक सेट विकसित कर रहा हूं जो एक सामान्य इंटरफ़ेस लागू करता है। मेरी लाइब्रेरी का उपभोक्ता इन वर्गों में से प्रत्येक को स्थिर कार्यों के एक निश्चित सेट को लागू करने की अपेक्षा करेगा। क्या वैसे भी है कि मैं इन वर्गों को सजाने के लिए कर सकता हूं ताकि संकलक उस मामले को पकड़ लेगा जहां कार्यों में से एक लागू नहीं किया गया है।क्या कुछ स्थिर कार्यों को लागू करने के लिए सी # कक्षा को मजबूर करने का कोई तरीका है?

मुझे पता है कि उपभोग करने वाले कोड के निर्माण के दौरान अंत में पकड़ा जाएगा। और मैं यह भी जानता हूं कि फैक्ट्री क्लास का उपयोग करके इस समस्या को कैसे प्राप्त किया जाए।

कक्षा में स्थैतिक कार्यों की आवश्यकता के लिए वहां कोई वाक्यविन्यास/गुण मौजूद है या नहीं, यह जानने के लिए उत्सुक है।

एड भ्रम से बचने के लिए 'इंटरफ़ेस' शब्द को हटा दिया गया।

+0

मेरी जिज्ञासा क्षमा करें, लेकिन मैं सोचने में मदद नहीं कर सकता कि आपको इस तरह की सुविधा क्यों चाहिए? स्थैतिक तरीकों का क्या सामान्य उदाहरण है (गैर स्थैतिक) तरीकों में नहीं है? मेरे दिमाग में कुछ भी नहीं आता है। अपने प्रश्न के लिए कुछ संदर्भ साझा करने की तरह लग रहा है? – Dan

+2

आपको स्थैतिक विधि कॉल करने के लिए किसी उदाहरण की आवश्यकता नहीं है। इसलिए वे फैक्ट्री विधियों के रूप में उपयोग करने के लिए अच्छे हैं, उदाहरण के लिए एक डी-सीरियलाइज विधि। – tpower

+0

@ डैन: एक अतिरिक्त उपयोग इंटरफ़ेस का उपयोग करने के बिना यह जानने के बिना होगा कि आप किसी उदाहरण या किसी प्रकार (या बाद में इसे बदल रहे हैं) पर काम कर रहे हैं या नहीं। एक स्थिर वर्ग के बारे में सोचें जो किसी प्रकार की सिंगलटन सूची का प्रतिनिधित्व करता है - और इसे उचित सूची के रूप में, 'IList ' लागू करना चाहिए। निश्चित रूप से, स्थिर वर्ग में 'IList ' लागू करने वाली कक्षा के उदाहरण को संग्रहीत करने का काम संभव है (और मुझे पता है कि वर्तमान में सी # वर्तमान में केवल इस तरह की अनुमति देता है), लेकिन क्लासिक रूप से क्लासिक रूप से घोषित करने की क्षमता एक इंटरफ़ेस को कार्यान्वित करना अप्रत्यक्ष स्तर का संकेत हटा देगा। –

उत्तर

28

नहीं, सी # में इसके लिए कोई भाषा समर्थन नहीं है। दो कामकाज हैं जिन्हें मैं तत्काल सोच सकता हूं:

  • रनटाइम पर प्रतिबिंब का उपयोग करें; पार उंगलियों और आशा ...
  • एक सिंगलटन/डिफ़ॉल्ट-उदाहरण/समान का उपयोग एक अंतरफलक है कि तरीकों

(अद्यतन)

असल में वाणी लागू करने के लिए, जब तक आप इकाई है के रूप में -स्टेस्टिंग, पहला विकल्प वास्तव में बुरा नहीं है जैसा कि आप सोच सकते हैं कि (जैसे मुझे) आप सख्त "स्थैतिक टाइपिंग" पृष्ठभूमि से आते हैं। तथ्य यह है; यह गतिशील भाषाओं में ठीक काम करता है। और वास्तव में, यह ठीक है कि मेरा generic operators कोड काम करता है - यह आशा आपके पास स्थिर ऑपरेटर हैं। रनटाइम पर, यदि आप नहीं करते हैं, तो यह आपके लिए एक उपयुक्त मॉकिंग टोन में हंस जाएगा ... लेकिन यह संकलन-समय पर जांच नहीं कर सकता है।

+11

अगर मैं उपयुक्त मॉकिंग टोन में कोड हँसे तो मुझे यह पसंद आएगा। रुको, वह हर समय होगा। कोई बात नहीं। ;-) –

4

दुर्भाग्यवश, नहीं, इस भाषा में निर्मित कुछ भी नहीं है।

0

नहीं, इस सुविधा में कोई बात नहीं होगी। इंटरफ़ेस मूल रूप से एकाधिक विरासत का एक स्केल डाउन रूप है। वे संकलक को वर्चुअल फ़ंक्शन टेबल सेट अप करने के बारे में बताते हैं ताकि गैर-स्थैतिक वर्चुअल विधियों को वंश वर्गों में ठीक से बुलाया जा सके। स्टेटिक विधियां आभासी नहीं हो सकती हैं, इसलिए, उनके लिए इंटरफेस का उपयोग करने में कोई बात नहीं है।

+2

निश्चित रूप से * इसमें * एक बिंदु है - सिर्फ इसलिए कि इंटरफ़ेस के माध्यम से विधियों को नहीं कहा जाएगा, इसका मतलब यह नहीं है कि यह परीक्षण करने योग्य नहीं है कि वे वहां हैं। यह नई टी() बाधा की तरह थोड़ा सा है जो सी # खुलासा करता है - नए टी() का वास्तविक कार्यान्वयन प्रभावी रूप से प्रतिबिंब के माध्यम से जाता है ... –

+0

मैं नहीं चाहता कि वे आभासी बनें, बस उन्हें अस्तित्व में मजबूर करें। – tpower

+0

मैं इस पर dsimcha के साथ हूँ। यदि स्पष्ट रूप से घोषित इंटरफ़ेस का उद्देश्य कार्यान्वयन से इंटरफ़ेस को अलग नहीं करना है, तो वहां "इंटरफ़ेस" शेष नहीं है। यदि आपको आवश्यकता है कि कुछ वर्गों में कुछ विधियां हैं, तो आप कुछ अन्य languge तत्व का आविष्कार कर सकते हैं, जैसे HasToImplementMethodsAttrib – Dan

15

नहीं। असल में ऐसा लगता है जैसे आप "स्थैतिक बहुरूपता" के बाद हैं। यह सी # में मौजूद नहीं है, हालांकि मैंने "static interface" notion which could be useful in terms of generics का एक प्रकार सुझाया है।

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

+0

कोई इंटरफ़ेस अनुबंध में निर्दिष्ट कर सकता है कि इंटरफ़ेस के सभी * वैध * कार्यान्वयन में कुछ स्थिर सदस्य * और * होना चाहिए, यदि अनदेखा हो, तो उनके विरासत अनुबंध में एक आवश्यकता है कि सभी * वैध * व्युत्पन्न प्रकारों को एक ही आवश्यकता से पालन करना चाहिए। इससे लोगों को इंटरफेस के अवैध कार्यान्वयन लिखने से रोका नहीं जा सकता है, लेकिन स्थिति किसी भी अन्य प्रकार के इंटरफ़ेस से भी बदतर नहीं होगी। – supercat

+0

@supercat: "अनुबंध" से आपका मतलब सिर्फ "दस्तावेज" या कोड अनुबंध जैसे कुछ है? –

+0

मेरा मतलब दस्तावेज था। किसी भी सार्थक इंटरफ़ेस में आवश्यकताओं का एक सेट होना चाहिए, जैसे कि उन आवश्यकताओं को पूरा करने वाले कार्यान्वयन वैध हैं, और उन आवश्यकताओं को पूरा नहीं करने वाले कार्यान्वयन अवैध हैं। कोई निश्चित प्रारूप नहीं है जिसमें ऐसी आवश्यकताओं को व्यक्त किया जाना चाहिए, लेकिन यदि उदा। 'IList के एक कार्यान्वयन' एक संपत्ति सेटर कि 'index' पैरामीटर नजरअंदाज कर दिया और एक यादृच्छिक तत्व बस अधिलेखित कर दिया, कई तरीके है कि साथ काम करने की उम्मीद थी एक' IList 'विफल हो जाएगा, इसलिए नहीं कि तरीकों दोषपूर्ण थे, लेकिन क्योंकि 'IList ' कार्यान्वयन अवैध था। – supercat

3

हालांकि इसके लिए कोई भाषा समर्थन नहीं है, आप इसे लागू करने के लिए एक स्थिर विश्लेषण उपकरण का उपयोग कर सकते हैं। उदाहरण के लिए, आप FxCop के लिए एक कस्टम नियम लिख सकते हैं जो किसी वर्ग पर एक विशेषता या इंटरफ़ेस कार्यान्वयन का पता लगाता है और फिर कुछ स्थैतिक तरीकों के अस्तित्व की जांच करता है।

0

जिस दृष्टिकोण से आपको आवश्यकता है, वह एक सिंगलटन है, जैसा कि मार्क ग्रेवेल ने सुझाव दिया था।

इंटरफेस, अन्य चीजों के साथ, आप अपने वर्गों में कुछ स्तर का अमूर्तता प्रदान करते हैं ताकि आप किसी दिए गए एपीआई का उपयोग कर सकें जो कि इसे लागू करता है। हालांकि, चूंकि आपको इसका उपयोग करने के लिए एक स्थिर वर्ग के प्रकार को जानने की आवश्यकता है, तो आप उस वर्ग को कार्यों के एक समूह को लागू करने के लिए क्यों लागू करना चाहते हैं?

हो सकता है कि आप [ImplementsXXXInterface] जैसे कस्टम एट्रिब्यूट का उपयोग कर सकें और यह सुनिश्चित करने के लिए कुछ रन टाइम चेकिंग प्रदान कर सकें कि इस विशेषता वाले वर्ग वास्तव में आपको आवश्यक इंटरफ़ेस को कार्यान्वित करते हैं?

+0

रनटाइम चेकिंग अच्छा नहीं है क्योंकि यह पहले से ही जब उपभोक्ता कोड के निर्माण संकलक द्वारा उठाया जाएगा। बस सोच रहा हूं कि क्या मैं संकलक को इसे पहले लेने के लिए प्राप्त कर सकता हूं। – tpower

1

सिंगलटन पैटर्न सभी मामलों में मदद नहीं करता है। मेरा उदाहरण मेरी वास्तविक परियोजना से है। यह नहीं हुआ है।

मेरे पास एक कक्षा है (चलिए इसे "विजेट" कहते हैं) जो किसी तृतीय पक्ष ORM में कक्षा से विरासत में मिलता है। अगर मैं एक विजेट ऑब्जेक्ट को तुरंत चालू करता हूं (इसलिए डीबी में एक पंक्ति बना रहा हूं) यह सुनिश्चित करने के लिए कि मेरी स्थिर विधियां घोषित की गई हैं, मैं जिसकी सफाई करने की कोशिश कर रहा हूं उससे बड़ा गड़बड़ कर रहा हूं।

अगर मैं डेटा की दुकान में इस अतिरिक्त वस्तु बनाने, मैं उन, गणना से छिपाना मिल गया है, आदि

मैं सी # में इंटरफेस का उपयोग सुनिश्चित करें कि मैं का एक सेट में आम सुविधाओं को लागू करने के लिए कक्षाएं।

इन सुविधाओं को लागू करने वाली कुछ विधियों के लिए इंस्टेंस डेटा चलाने की आवश्यकता होती है। मैं इन तरीकों को उदाहरण विधियों के रूप में कोड करता हूं, और यह सुनिश्चित करने के लिए कि वे कक्षा में मौजूद हैं, एक सी # इंटरफ़ेस का उपयोग करें।

इनमें से कुछ विधियों को आवृत्ति डेटा की आवश्यकता नहीं है, इसलिए वे स्थिर तरीके हैं। अगर मैं स्थिर तरीकों के साथ इंटरफेस घोषित कर सकता हूं, तो संकलक यह जांच सकता है कि क्लास में ये विधियां मौजूद हैं या नहीं, जो कहती हैं कि यह इंटरफ़ेस लागू करती है।

5

यह एक अच्छा सवाल है और एक जिसे मैंने अपनी परियोजनाओं में सामना किया है।

कुछ लोग मानते हैं कि इंटरफेस और अमूर्त वर्ग केवल पॉलिमॉर्फिज्म के लिए मौजूद हैं, न कि कुछ तरीकों को लागू करने के लिए मजबूर करने के लिए। व्यक्तिगत रूप से, मैं पॉलिमॉर्फिज्म को प्राथमिक उपयोग के मामले पर विचार करता हूं, और एक माध्यमिक कार्यान्वयन को मजबूर करता हूं। मैं अक्सर मजबूर कार्यान्वयन तकनीक का उपयोग अक्सर करता हूं। आमतौर पर, यह टेम्पलेट पैटर्न को लागू करने वाले ढांचे कोड में दिखाई देता है। आधार/टेम्पलेट वर्ग कुछ जटिल विचारों को समाहित करता है, और उप-वर्ग अमूर्त तरीकों को लागू करके कई भिन्नताएं प्रदान करते हैं। एक व्यावहारिक लाभ यह है कि सार तत्व उप-वर्गों को लागू करने वाले अन्य डेवलपर्स को मार्गदर्शन प्रदान करते हैं। विजुअल स्टूडियो में आपके लिए विधियों को रोकने की क्षमता भी है। यह विशेष रूप से सहायक होता है जब रखरखाव डेवलपर को नए उप-वर्ग महीने या साल बाद जोड़ना पड़ता है।

नकारात्मकता यह है कि सी # में इनमें से कुछ टेम्पलेट परिदृश्यों के लिए कोई विशिष्ट समर्थन नहीं है। स्टेटिक विधियां एक हैं। एक और रचनाकार है; आदर्श रूप से, आईएसरियलज़ेबल को संरक्षक को संरक्षित क्रमिकरण कन्स्ट्रक्टर को लागू करने के लिए मजबूर होना चाहिए।

वांछित प्रकारों पर स्थिर विधि लागू करने के लिए स्वचालित परीक्षण का उपयोग करने के लिए संभवतः सबसे आसान दृष्टिकोण (जैसा कि पहले सुझाया गया है) है। एक और व्यवहार्य विचार पहले से ही उल्लेख किया गया है एक स्थिर विश्लेषण नियम लागू करना है।

एक तीसरा विकल्प एक अनुमान-उन्मुख प्रोग्रामिंग ढांचे का उपयोग करना है जैसे कि PostSharp। PostSharp पहलुओं के संकलन-समय सत्यापन का समर्थन करता है। आप .NET कोड लिख सकते हैं जो संकलन समय पर असेंबली पर प्रतिबिंबित करता है, मनमानी चेतावनियां और त्रुटियां उत्पन्न करता है। आम तौर पर, आप यह सत्यापित करने के लिए करते हैं कि एक पहलू उपयोग उचित है, लेकिन मुझे नहीं लगता कि आप टेम्पलेट नियमों को मान्य करने के लिए इसका उपयोग क्यों नहीं कर सके।

0

तो आप सिर्फ उन संकलक त्रुटियों प्राप्त करने के बाद कर रहे हैं, इस स्थापना पर विचार करें:

  1. एक अंतरफलक में तरीकों को परिभाषित करें।
  2. अमूर्त के साथ विधियों की घोषणा करें।
  3. सार्वजनिक स्थैतिक तरीकों को लागू करें, और सार विधि ओवरराइड बस स्थिर तरीकों को कॉल करें।

यह अतिरिक्त कोड का एक छोटा सा है, लेकिन क्या आप जानते हैं कि जब कोई एक आवश्यक विधि को लागू नहीं किया गया है जाएगा।

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

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