डी

2011-09-23 9 views
5

में एक फ़ंक्शन में एक फ़ंक्शन में विविधता तर्कों को पास करना मेरे पास एक विविध डी-स्टाइल फ़ंक्शन foo(format, ...) है, जो writefln के आसपास एक रैपर है। मैं इस तरह कुछ करने के लिए करना चाहते हैं:डी

foo(format, <...>) { 
    //... 
    writefln(format, ...); 
} 

अनिवार्य रूप से, अंडाकार पैरामीटर (ओं) पर गुजर writefln करने के लिए। मैं समझता हूं कि सी/सी ++ में यह आसान/संभव नहीं है, लेकिन क्या डी में इसे पूरा करने का कोई तरीका है?

+0

धन्यवाद, यह पता चला है कि टेम्पलेट्स ने इस मुद्दे को बहुत साफ और सुंदर तरीके से हल किया है। जोड़ा गया बोनस: यह किसी भी स्मृति आवंटन का कारण नहीं बनता है, इसलिए इसे विनाशकों से कहा जा सकता है (यह लॉगिंग मॉड्यूल से एक फ़ंक्शन है)। –

उत्तर

4

यह यह तुम्हारे लिए क्या करेंगे:

import std.stdio; 
void customWrite(Args...)(string format, Args args) 
{ 
    writefln(format, args); 
} 
3

आप टेम्पलेट्स चाहते हैं, आप इसे इस तरह कर सकते हैं:

auto bar(T...)(T args) { ... } 

auto foo(T...)(T args) 
{ 
    return bar!T(args); 
} 

लेकिन अगर आप रन-टाइम variadic तर्क हों, तो आपको क्या करना है सी करता है: "वी के _argptr पारित -वृत्त "आपके कार्य, उदाहरण के लिए vprintf

+0

यह 'बार (तर्क)' हो सकता है। आपको '! टी' की आवश्यकता नहीं होनी चाहिए। –

+1

@ जोनाथनएमडाविस: हाँ, मुझे एहसास है। लेकिन जब मैं एक जेनेरिक को दूसरे से कॉल करते समय हमेशा इसे स्पष्ट रूप से लिखता हूं क्योंकि यह अक्सर संकलक त्रुटियों को ढूंढना आसान बनाता है।(कहने के बजाय "मुझे कोई मैच नहीं मिल रहा है", यह वास्तव में आपको बताता है कि यह क्या मिलान नहीं कर सका।) – Mehrdad

+0

@ मेहरदाद: एक उल्लेखनीय तकनीक! – vines

4

मैं भूल गया था यहां तक ​​कि डी में ही अस्तित्व में variadics के उन प्रकार मुझे नहीं लगता कि कि कि TDPL यहां तक ​​कि उन्हें का उल्लेख है। मुझे विश्वास है कि यह है कि डी में variadics के 4 विभिन्न प्रकार के कुल योग

  1. सी variadics TypeInfo

    void func(string format, ...) {...} 
    
  2. सजातीय variadics सरणियों उपयोग करने के साथ

    extern(C) void func(string format, ...) {...} 
    
  3. डी variadics बनाता है

    void func(string format, string[] args...) {...} 
    
  4. विषम variadics टेम्पलेट का उपयोग कर variadics

    void func(T...)(string format, args) {...} 
    

मुझे विश्वास है कि TDPL वास्तव में केवल बात करती है # के बारे में 3 और # 4, और उन सभी कि मैं सामान्य रूप से उपयोग कर रहे हैं, तो मैं करने के लिए खुदाई जाना होगा # 2 का उपयोग करके तर्कों को पारित करने का तरीका जानें। मुझे उम्मीद है कि यह सी # में सी के साथ ऐसा कैसे होता है, लेकिन मुझे नहीं पता।

हालांकि, यह # 3 और # 4 के साथ आसान है। दोनों स्थितियों में, आप बस args पास कर सकते हैं जो भी आप इसे पास करना चाहते हैं। और दोनों इंडेक्सिंग और स्लाइसिंग (उदा। args[1] और args[1 .. $]) के साथ-साथ length संपत्ति रखने की अनुमति देते हैं। इसलिए, वे उपयोग करने में आसान हैं, और अधिकांश भाग के लिए, वे जाने का बेहतर तरीका हैं। एकमात्र अपवाद जिन्हें मैं सोच सकता हूं, यदि आप मौजूदा सी फ़ंक्शन को कॉल कर रहे हैं (इस मामले में, आप # 1 का उपयोग करते हैं) या यदि आपको विषम टेम्पलेट्स की आवश्यकता है और बाइनरी आकार में वृद्धि का खर्च नहीं उठा सकता है जिसमें टेम्पलेट्स बनाते हैं (जिसमें यदि आप # 2 का उपयोग करते हैं), जो वास्तव में एम्बेडेड वातावरण में केवल एक मुद्दा होना चाहिए। आम तौर पर, # 3 और # 4 और केवल सादे बेहतर समाधान।

+1

थोड़ा और नीचे देखें http://www.d-programming-language.org/function.html#variadic: # 3 कक्षाओं के साथ भी काम करता है। – BCS