/ / क्या मैक्रो का उपयोग करके स्काला विधि तर्कों को सरल बनाना संभव है? - स्केला, मैक्रोज़, स्केला -२.१०

क्या मैक्रोज़ का उपयोग करके स्कैला विधि तर्क घोषणा को सरल बनाना संभव है? - स्कैला, मैक्रोज़, स्कैला-2.10

तरीकों को अक्सर स्पष्ट पैरामीटर नामों के साथ घोषित किया जाता है, उदा।

def myMethod(s: String, image: BufferedImage, mesh: Mesh) { ... }

पैरामीटर नाम पैरामीटर प्रकार के अनुरूप हैं।

1) "एस" का उपयोग अक्सर स्ट्रिंग के लिए किया जाता है

2) Int के लिए "i"

3) एक शब्द वर्गों (मेष -> जाल) के लिए निम्न श्रेणी का नाम

4) लंबे वर्ग के नाम के लिए वर्ग नाम से अंतिम शब्द नीचा (बफ़र्डमैज -> छवि)

(बेशक, यह सभी तरीकों और तर्कों के लिए सुविधाजनक नहीं होगा। बेशक, कोई अन्य नियमों को पसंद करेगा ...)

स्काला मैक्रों का उद्देश्य कोड में कुछ भाव उत्पन्न करना है। मैं कुछ विशिष्ट मैक्रोज़ लिखना चाहूंगा ताकि स्कैला के भावों को कुछ इस तरह बदला जा सके।

// "arguments interpolation" style
// like string interpolation
def myMethod s[String, BufferedImage, Mesh]
{ /* code using vars "s", "image", "mesh" */ }

// or even better:
mydef myMethod[String, BufferedImage, Mesh]
{ /* code using vars "s", "image", "mesh" */ }

क्या यह संभव है?

उत्तर:

जवाब के लिए 2 № 1

वर्तमान में यह संभव नहीं है और शायद यह होगाकभी नहीं। मैक्रों अपने स्वयं के वाक्यविन्यास का परिचय नहीं दे सकते हैं - उन्हें वैध स्काला कोड (जिसे संकलन समय पर निष्पादित किया जा सकता है) के माध्यम से प्रस्तुत किया जाना चाहिए, और, उन्हें मान्य स्काला कोड (बेहतर वैध एएसटी एएसटी कहना चाहिए) उत्पन्न करना चाहिए।

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

forM({i = 0; i < 10; i += 1}) {
println(i)
}

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

इस मैक्रो का कार्यान्वयन इस तरह दिखता है:

def forM(header: _)(body: _) = macro __forM

def __forM(c: Context)(header: c.Tree)(body: c.Tree): c.Tree = {
import c.universe._
header match {
case Block(
List(
Assign(Ident(TermName(name)), Literal(Constant(start))),
Apply(Select(Ident(TermName(name2)), TermName(comparison)), List(Literal(Constant(end))))
),
Apply(Select(Ident(TermName(name3)), TermName(incrementation)), List(Literal(Constant(inc))))
) =>

// here one can generate the behavior of the loop
// but omit full implementation for clarity now ...

}
}

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

वर्तमान में थोड़ा है प्रलेखन उपलब्ध है, लेकिन क्योंकि यह बहुत बीटा है बहुत सारी चीजें शायद भविष्य में बदल जाएंगी।

टाइप मैक्रोज़ के साथ कुछ इस तरह लिखना संभव है:

object O extends M {
// traverse the body of O to find what you want
}

type M(x: _) = macro __M

def __M(c: Context)(x: c.Tree): c.Tree = {
// omit full implementation for clarity ...
}

यह पूरे शरीर को टाइप करने में देरी करने के लिए अच्छा है क्योंकि यह चीजों को ठंडा करने की अनुमति देता है ...


मैक्रों जो स्केलस सिंटैक्स को बदल सकते हैं, फिलहाल योजनाबद्ध नहीं हैं और शायद एक अच्छा विचार नहीं है। मैं यह नहीं कह सकता कि क्या वे एक दिन होंगे केवल भविष्य हमें यह बता सकता है।


जवाब के लिए 2 № 2

"क्यों" के अलावा (वास्तव में, आप ऐसा क्यों करना चाहते हैं?), इसका उत्तर नहीं है, क्योंकि जहां तक ​​मुझे पता है कि मैक्रोज़ (उनकी वर्तमान स्थिति में) तरीके या प्रकार उत्पन्न नहीं कर सकते हैं, केवल अभिव्यक्ति।