प्रोग्रामर 5.1 के लिए Kotlin बूटकैंप: एक्सटेंशन

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

परिचय

इस कोडलैब में आपको Kotlin में कई अलग-अलग काम की सुविधाओं के बारे में जानकारी दी गई है. इनमें पेयर, कलेक्शन, और एक्सटेंशन फ़ंक्शन शामिल हैं.

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

आपको क्या पता होना चाहिए

  • Kotlin के फ़ंक्शन, क्लास, और मेथड का सिंटैक्स
  • IntelliJ IDEA में Kotlin's REPL (Read-Eval-Print Loop) के साथ काम करने का तरीका
  • IntelliJ IDEA में नई क्लास बनाने और कोई प्रोग्राम चलाने का तरीका

आप इन चीज़ों के बारे में जानेंगे

  • जोड़े और तीन लोगों के साथ काम करने का तरीका
  • कलेक्शन के बारे में ज़्यादा जानकारी
  • कॉन्सटेंट तय करना और उनका इस्तेमाल करना
  • राइटिंग एक्सटेंशन फ़ंक्शन

आप क्या कर पाएंगे!

  • REPL में जोड़े गए तीन तरीकों के बारे में जानें
  • कॉन्सटेंट व्यवस्थित करने के अलग-अलग तरीके जानें
  • एक्सटेंशन फ़ंक्शन और एक्सटेंशन प्रॉपर्टी लिखें

इस टास्क में, आपको जोड़ों और तीन लोगों के बारे में पता चलता है. साथ ही, इन्हें मिटाने के बारे में भी बताया जाता है. दो या तीन सामान्य आइटम के लिए, पेयर और ट्रिपल पहले से तैयार डेटा क्लास होते हैं. उदाहरण के लिए, फ़ंक्शन के एक से ज़्यादा मान लौटाने में यह उपयोगी हो सकता है.

मान लें कि आपके पास List मछली थी और एक फ़ंक्शन isFreshWater() था, ताकि यह पता चल सके कि मछली ताज़े पानी की है या खारे पानी की. List.partition() दो सूचियां लौटाता है, एक उन आइटम के लिए जिनमें स्थिति true है. दूसरे आइटम उन आइटम के लिए होते हैं जिनकी स्थिति false है.

val twoLists = fish.partition { isFreshWater(it) }
println("freshwater: ${twoLists.first}")
println("saltwater: ${twoLists.second}")

पहला चरण: कुछ जोड़ों और तीन जगहों की योजना बनाना

  1. REPL (टूल > Kotlin > Kotlin REPL) खोलें.
  2. उपकरण के एक हिस्से को इसके उपयोग के साथ जोड़कर एक जोड़ी बनाएं, फिर मानों को प्रिंट करें. आप दो स्ट्रिंग, जैसे to स्ट्रिंग को जोड़कर एक एक्सप्रेशन बनाकर, फिर हर वैल्यू को रेफ़र करने के लिए .first या .second का इस्तेमाल करके एक जोड़ा बना सकते हैं.
val equipment = "fish net" to "catching fish"
println("${equipment.first} used for ${equipment.second}")
⇒ fish net used for catching fish
  1. एक ट्रिपल बनाएं और उसे toString() के साथ प्रिंट करें, फिर उसे toList() के साथ सूची में बदलें. आप तीन वैल्यू के साथ Triple() का इस्तेमाल करके तीन जगहें बनाते हैं. हर वैल्यू के बारे में बताने के लिए .first, .second, और .third का इस्तेमाल करें.
val numbers = Triple(6, 9, 42)
println(numbers.toString())
println(numbers.toList())
⇒ (6, 9, 42)
[6, 9, 42]

ऊपर दिए गए उदाहरणों में जोड़े या सभी तीन हिस्सों के लिए एक ही तरह का इस्तेमाल किया गया है, लेकिन यह ज़रूरी नहीं है. उदाहरण के लिए, स्ट्रिंग, संख्या या सूची एक हिस्से में हो सकती है, जैसे कि कोई दूसरा जोड़ा या तीन गुना.

  1. एक जोड़ा बनाएं जहां जोड़ी का पहला हिस्सा खुद एक जोड़ा हो.
val equipment2 = ("fish net" to "catching fish") to "equipment"
println("${equipment2.first} is ${equipment2.second}\n")
println("${equipment2.first.second}")
⇒ (fish net, catching fish) is equipment
⇒ catching fish

दूसरा चरण: कुछ जोड़ों और तीन जगहों को अलग करना

जोड़े और अलग-अलग हिस्सों को अलग-अलग हिस्सों में बांटने को डिस्ट्रक्चर कहा जाता है. वैरिएबल की सही संख्या (संख्या) को पेयर या ट्रिपल असाइन करें. साथ ही, Kotlin हर हिस्से का मान क्रम में असाइन करेगी.

  1. किसी जोड़े को अलग करें और वैल्यू प्रिंट करें.
val equipment = "fish net" to "catching fish"
val (tool, use) = equipment
println("$tool is used for $use")
⇒ fish net is used for catching fish
  1. तीन तरीकों से जानकारी को अलग करें और प्रिंट करें.
val numbers = Triple(6, 9, 42)
val (n1, n2, n3) = numbers
println("$n1 $n2 $n3")
⇒ 6 9 42

ध्यान दें कि जोड़े और तीन निशानों को नष्ट करने का काम, डेटा क्लास की तरह ही काम करता है. यह जानकारी पिछली कोडलैब (कोड बनाना सीखना) में भी दी गई थी.

इस टास्क में, आपको कलेक्शन के बारे में ज़्यादा जानकारी मिलेगी. इनमें सूचियां और नए तरह के कलेक्शन के साथ-साथ हैश मैप भी शामिल हैं.

पहला चरण: सूचियों के बारे में ज़्यादा जानें

  1. पहले के लेसन में, सूचियों और बदली जा सकने वाली सूचियों की जानकारी दी गई थी. ये डेटा स्ट्रक्चर बहुत काम का होता है, इसलिए Kotlin में सूचियों के लिए कई बिल्ट-इन फ़ंक्शन उपलब्ध होते हैं. सूचियों के लिए फ़ंक्शन की इस आंशिक सूची की समीक्षा करें. आपको List और MutableList के लिए, Kotlin दस्तावेज़ में पूरी लिस्टिंग मिल सकती है.

फ़ंक्शन

मकसद

add(element: E)

बदली जा सकने वाली सूची में कोई आइटम जोड़ें.

remove(element: E)

बदली जा सकने वाली सूची से किसी आइटम को हटाना.

reversed()

एलिमेंट की सूची की कॉपी रिवर्स ऑर्डर में दें.

contains(element: E)

अगर सूची में आइटम शामिल है, तो true दिखाएं.

subList(fromIndex: Int, toIndex: Int)

पहले इंडेक्स से लेकर दूसरे इंडेक्स को शामिल न करते हुए सूची का कुछ हिस्सा दिखाएं.

  1. अब भी REPL में काम कर रहा है. नंबर की सूची बनाएं और उस पर sum() को कॉल करें. यह सभी चीज़ों का योग करता है.
val list = listOf(1, 5, 3, 4)
println(list.sum())
⇒ 13
  1. स्ट्रिंग की सूची बनाएं और उसे जोड़ें.
val list2 = listOf("a", "bbb", "cc")
println(list2.sum())
⇒ error: none of the following functions can be called with the arguments supplied:
  1. अगर किसी एलिमेंट में List से अलग कोई डेटा है, जैसे कि स्ट्रिंग, तो आप यह तय कर सकते हैं कि lambda फ़ंक्शन के साथ .sumBy() का इस्तेमाल करके उसे कैसे जोड़ा जाए. उदाहरण के लिए, हर स्ट्रिंग की लंबाई के हिसाब से कुल योग. Lambda आर्ग्युमेंट का डिफ़ॉल्ट नाम it है. यहां it का इस्तेमाल करके, सूची के हर एलिमेंट के बारे में बताया गया है, क्योंकि सूची में पीछे की ओर जाता है.
val list2 = listOf("a", "bbb", "cc")
println(list2.sumBy { it.length })
⇒ 6
  1. सूचियों के साथ आप बहुत कुछ कर सकते हैं. सुविधा उपलब्ध देखने का एक तरीका IntelliJ IDEA में सूची बनाना, बिंदु जोड़ना, और टूलटिप में अपने-आप पूरा होने की सूची देखना है. यह किसी भी ऑब्जेक्ट के लिए काम करता है. इसे सूची के साथ आज़माएं.

  1. सूची से listIterator() चुनें, फिर for स्टेटमेंट की मदद से सूची देखें और स्पेस से अलग किए गए सभी एलिमेंट को प्रिंट करें.
val list2 = listOf("a", "bbb", "cc")
for (s in list2.listIterator()) {
    println("$s ")
}
⇒ a bbb cc

दूसरा चरण: हैश मैप को आज़माना

Kotlin में, hashMapOf() का इस्तेमाल करके, किसी भी चीज़ के साथ करीब-करीब हर चीज़ को मैप किया जा सकता है. हैश मैप, जोड़ों की एक सूची की तरह होते हैं, जहां पहला मान एक कुंजी के तौर पर काम करता है.

  1. एक ऐसा हैश मैप बनाएं जो लक्षणों, कुंजियों, और मछलियों के रोगों के मानों से मेल खाता हो.
val cures = hashMapOf("white spots" to "Ich", "red sores" to "hole disease")
  1. इसके बाद, आप लक्षण कुंजी के आधार पर, get() या इससे भी छोटे वर्गाकार ब्रैकेट [] का इस्तेमाल करके, बीमारी के मान को वापस पा सकते हैं.
println(cures.get("white spots"))
⇒ Ich
println(cures["red sores"])
⇒ hole disease
  1. ऐसा लक्षण बताएं जो मैप में #&39; नहीं हो.
println(cures["scale loss"])
⇒ null

अगर मैप में कोई कुंजी't है, तो मेल खाने वाली बीमारी को लौटाने की कोशिश करने पर null दिखता है. मैप डेटा के आधार पर, संभावित कुंजी के लिए कोई मैच नहीं होना आम बात हो सकती है. इस तरह के मामलों में, Kotlin में getOrDefault() फ़ंक्शन मिलता है.

  1. getOrDefault() का इस्तेमाल करके, ऐसी कुंजी खोजें जो मेल नहीं खाती.
println(cures.getOrDefault("bloating", "sorry, I don't know"))
⇒ sorry, I don't know

अगर आप सिर्फ़ वैल्यू रिटर्न करने के साथ-साथ और भी काम करना चाहते हैं, तो Kotlin में getOrElse() फ़ंक्शन मिलता है.

  1. getOrDefault() के बजाय getOrElse() का इस्तेमाल करने के लिए, अपना कोड बदलें.
println(cures.getOrElse("bloating") {"No cure for this"})
⇒ No cure for this

एक आसान डिफ़ॉल्ट वैल्यू देने के बजाय, कर्ली ब्रैकेट {} के बीच में जो भी कोड होता है उसे लागू किया जाता है. उदाहरण में, else सिर्फ़ एक स्ट्रिंग दिखाता है. हालांकि, यह एक वेबपेज की तरह है, जो किसी इलाज की मदद से वेबपेज ढूंढने और उसे लौटाने की तरह काम करता है.

mutableListOf की तरह ही आप भी mutableMapOf बना सकते हैं. बदले जा सकने वाले मैप की मदद से आप आइटम डाल और हटा सकते हैं. बदले जा सकने वाले का मतलब है, बदल नहीं सकते, नहीं बदले जा सकते.

  1. इन्वेंट्री का ऐसा मैप बनाएं जिसमें बदलाव किया जा सके. साथ ही, सामान की संख्या को सामान की संख्या के साथ मैप करें. मछली के नेट से इसे बनाएं, फिर put() की मदद से इन्वेंट्री में तीन टैंक स्क्रबर जोड़ें और remove() की मदद से फ़िश नेट हटाएं.
val inventory = mutableMapOf("fish net" to 1)
inventory.put("tank scrubber", 3)
println(inventory.toString())
inventory.remove("fish net")
println(inventory.toString())
⇒ {fish net=1, tank scrubber=3}{tank scrubber=3}

इस टास्क में, आपको Kotlin में कॉन्सटेंट और उन्हें व्यवस्थित करने के अलग-अलग तरीकों के बारे में पता चलेगा.

पहला चरण: कॉन्सट वैल्यू और वैल्यू के बारे में जानना

  1. REPL में, न्यूमेरिक कॉन्सटेंट बनाने की कोशिश करें. Kotlin में, const val का इस्तेमाल करके कंपाइल करने के समय, टॉप लेवल कॉन्सटेंट बनाया जा सकता है और उन्हें वैल्यू असाइन की जा सकती है.
const val rocks = 3

मान असाइन कर दिया गया है और इसे बदला नहीं जा सकता, जो कि नियमित val की जानकारी देने जैसा ही है. तो const val और val के बीच क्या अंतर है? const val की वैल्यू, कंपाइल करने के समय तय की जाती है. वहीं, val की वैल्यू प्रोग्राम के चलने के दौरान तय की जाती है. इसका मतलब है कि val को किसी रन टाइम के दौरान, किसी फ़ंक्शन से असाइन किया जा सकता है.

इसका मतलब है कि val को किसी फ़ंक्शन से वैल्यू असाइन की जा सकती है, लेकिन const val ऐसा नहीं कर सकता.

val value1 = complexFunctionCall() // OK
const val CONSTANT1 = complexFunctionCall() // NOT ok

इसके अलावा, const val सिर्फ़ टॉप लेवल पर काम करता है. साथ ही, सिंगलटन क्लास में यह काम object के साथ होता है, न कि सामान्य क्लास में. आप इसका इस्तेमाल ऐसी फ़ाइल या सिंगलटन ऑब्जेक्ट बनाने के लिए कर सकते हैं जिसमें सिर्फ़ कॉन्सटेंट होते हैं. साथ ही, उन्हें ज़रूरत के हिसाब से इंपोर्ट कर सकते हैं.

object Constants {
    const val CONSTANT2 = "object constant"
}
val foo = Constants.CONSTANT2

दूसरा चरण: कंपैनियन ऑब्जेक्ट बनाना

Kotlin में क्लास लेवल कॉन्सटेंट का कॉन्सेप्ट नहीं होता.

किसी क्लास में कॉन्सटेंट (स्थायी) को परिभाषित करने के लिए, आपको उन्हें companion कीवर्ड के साथ बताए गए कंपैनियन ऑब्जेक्ट में रैप करना होगा. कंपैनियन ऑब्जेक्ट, मूल रूप से क्लास के अंदर एक सिंगलटन ऑब्जेक्ट होता है.

  1. स्ट्रिंग कॉन्सटेंट वाली कंपैनियन ऑब्जेक्ट वाली क्लास बनाएं.
class MyClass {
    companion object {
        const val CONSTANT3 = "constant in companion"
    }
}

कंपैनियन ऑब्जेक्ट और रेगुलर ऑब्जेक्ट के बीच बुनियादी फ़र्क़ है:

  • कंपैनियन ऑब्जेक्ट को, शामिल क्लास के स्टैटिक कंस्ट्रक्टर से शुरू किया जाता है. यानी, जब ऑब्जेक्ट बनाया जाता है, तब ये ऑब्जेक्ट बनते हैं.
  • नियमित ऑब्जेक्ट को उस ऑब्जेक्ट के पहले ऐक्सेस पर लेज़ी तरीके से शुरू किया जाता है; यानी कि जब उन्हें पहली बार इस्तेमाल किया जाता है.

इसमें और भी बातें हैं, लेकिन इस समय एक साथी ऑब्जेक्ट में क्लास में कॉन्सटेंट रैप करने की ज़रूरत है.

इस टास्क में, आप क्लास के व्यवहार को बढ़ाने के बारे में जानेंगे. यूआरएल की क्लास के व्यवहार को बढ़ाने के लिए, उपयोगिता फ़ंक्शन लिखना बहुत आम है. Kotlin, इन उपयोगिता फ़ंक्शन के एलान के लिए एक आसान सिंटैक्स उपलब्ध कराती है: एक्सटेंशन फ़ंक्शन.

एक्सटेंशन फ़ंक्शन की मदद से, आप किसी मौजूदा क्लास में फ़ंक्शन जोड़ सकते हैं. इसके लिए आपको सोर्स कोड को ऐक्सेस करने की ज़रूरत नहीं है. उदाहरण के लिए, आप उन्हें एक extensions.kt फ़ाइल में एलान कर सकते हैं जो आपके पैकेज का हिस्सा है. यह क्लास को असल में संशोधित नहीं करता, लेकिन इससे आप उस क्लास के ऑब्जेक्ट पर फ़ंक्शन को कॉल करते समय डॉट-नोटेशन का उपयोग कर सकते हैं.

पहला चरण: एक्सटेंशन फ़ंक्शन लिखना

  1. अब भी REPL में काम कर रहा है. यह देखने के लिए कि किसी स्ट्रिंग में खाली जगहें हैं या नहीं, hasSpaces() एक आसान एक्सटेंशन फ़ंक्शन लिखें. फ़ंक्शन का नाम उस क्लास से शुरू होता है जिस पर यह काम करता है. फ़ंक्शन के अंदर, this उस ऑब्जेक्ट को दिखाता है जिस पर इसे कॉल किया जाता है और it, find() कॉल में इटरेटर की जानकारी देता है.
fun String.hasSpaces(): Boolean {
    val found = this.find { it == ' ' }
    return found != null
}
println("Does it have spaces?".hasSpaces())
⇒ true
  1. आप hasSpaces() फ़ंक्शन को आसान बना सकते हैं. this साफ़ तौर पर ज़रूरी नहीं है और फ़ंक्शन को सिंगल एक्सप्रेशन तक कम किया जा सकता है और दिखाया जा सकता है. इसलिए, इसके आस-पास कर्ली ब्रैकेट {} भी नहीं होने चाहिए.
fun String.hasSpaces() = find { it == ' ' } != null

दूसरा चरण: एक्सटेंशन की सीमाओं के बारे में जानना

एक्सटेंशन फ़ंक्शन के पास सिर्फ़ उस क्लास के सार्वजनिक एपीआई का ऐक्सेस होता है जिसे वे बड़ा कर रहे हैं. जो वैरिएबल private हैं उन्हें ऐक्सेस नहीं किया जा सकता.#39;

  1. private वाली प्रॉपर्टी में एक्सटेंशन फ़ंक्शन जोड़ने की कोशिश करें.
class AquariumPlant(val color: String, private val size: Int)

fun AquariumPlant.isRed() = color == "red"    // OK
fun AquariumPlant.isBig() = size > 50         // gives error
⇒ error: cannot access 'size': it is private in 'AquariumPlant'
  1. नीचे दिए गए कोड की जांच करें और पता लगाएं कि वह क्या प्रिंट करेगा.
open class AquariumPlant(val color: String, private val size: Int)

class GreenLeafyPlant(size: Int) : AquariumPlant("green", size)

fun AquariumPlant.print() = println("AquariumPlant")
fun GreenLeafyPlant.print() = println("GreenLeafyPlant")

val plant = GreenLeafyPlant(size = 10)
plant.print()
println("\n")
val aquariumPlant: AquariumPlant = plant
aquariumPlant.print()  // what will it print?
⇒ GreenLeafyPlant
AquariumPlant

plant.print() का GreenLeafyPlant प्रिंट है. हो सकता है कि आप aquariumPlant.print() के लिए भी GreenLeafyPlant प्रिंट कर लें, क्योंकि इसे plant की वैल्यू असाइन की गई थी. हालांकि, टाइप को कंपाइल करने के दौरान रिज़ॉल्व किया जाता है, ताकि AquariumPlant प्रिंट हो सके.

तीसरा चरण: एक्सटेंशन प्रॉपर्टी जोड़ना

एक्सटेंशन के अलावा, Kotlin की मदद से एक्सटेंशन प्रॉपर्टी भी जोड़ी जा सकती हैं. एक्सटेंशन फ़ंक्शन की तरह, आप उस क्लास का नाम भी बढ़ा रहे हैं जिसे आप #33

  1. REPL में अब भी काम कर रहा है. AquariumPlant में एक एक्सटेंशन प्रॉपर्टी जोड़ें. इसका रंग हरा होने पर, true दिखेगा.
val AquariumPlant.isGreen: Boolean
   get() = color == "green"

isGreen प्रॉपर्टी को किसी सामान्य प्रॉपर्टी की तरह ही ऐक्सेस किया जा सकता है; ऐक्सेस किए जाने पर, isGreen के लिए गैटर को मान पाने के लिए कॉल किया जाता है.

  1. aquariumPlant वैरिएबल के लिए isGreen प्रॉपर्टी को प्रिंट करें और नतीजे पर नज़र रखें.
aquariumPlant.isGreen
⇒ res4: kotlin.Boolean = true

चौथा चरण: शून्य पाने वाले लोगों के बारे में जानना

जिस क्लास को आप एक्सटेंड करते हैं उसे रिसीवर कहते हैं. इसकी क्लास को शून्य किया जा सकता है. अगर आप ऐसा करते हैं, तो मुख्य हिस्से में इस्तेमाल किया गया this वैरिएबल null हो सकता है. इसलिए, यह पक्का करें कि आपने उसकी जांच की हो. अगर आपको लगता है कि कॉल करने वाले लोग, आपके एक्सटेंशन के तरीके को शून्य वाले वैरिएबल पर कॉल करना चाहते हैं या जब आप अपना फ़ंक्शन null पर लागू करेंगे, तब डिफ़ॉल्ट व्यवहार देना चाहते हैं. इसके लिए, आपको शून्य होने वाले रिसीवर का इस्तेमाल करना होगा.

  1. अब भी REPL में काम कर रहा है. pull() का तरीका तय करें, जो शून्य होने वाले रिसीवर का इस्तेमाल करता हो. यह टाइप के बाद, डॉट से पहले, सवाल के निशान ? से दिखाया जाता है. बॉडी के अंदर, आप प्रश्न-बिंदु-लागू करें ?.apply. का उपयोग करके जाँच कर सकते हैं कि this null नहीं हैं
fun AquariumPlant?.pull() {
   this?.apply {
       println("removing $this")
   }
}

val plant: AquariumPlant? = null
plant.pull()
  1. इस मामले में, जब आप प्रोग्राम चलाते हैं, तो कोई आउटपुट नहीं मिलता. क्योंकि plant null है, इसलिए आंतरिक println() को कॉल नहीं किया जाता.

एक्सटेंशन के फ़ंक्शन बहुत असरदार होते हैं और ज़्यादातर Kotlin स्टैंडर्ड लाइब्रेरी को एक्सटेंशन फ़ंक्शन के तौर पर लागू किया जाता है.

इस लेसन में, कलेक्शन के बारे में ज़्यादा जाना, कॉन्सटेंट के बारे में सीखा, और एक्सटेंशन फ़ंक्शन और प्रॉपर्टी की ताकत के बारे में सीखा.

  • फ़ंक्शन के जोड़े की एक से ज़्यादा वैल्यू दिखाने के लिए, पेयर और ट्रिपल का इस्तेमाल किया जा सकता है. उदाहरण के लिए:
    val twoLists = fish.partition { isFreshWater(it) }
  • Kotlin में List के लिए कई काम के फ़ंक्शन होते हैं, जैसे कि reversed(), contains(), और subList().
  • कुंजियों का मान मैप करने के लिए, HashMap का इस्तेमाल किया जा सकता है. उदाहरण के लिए:
    val cures = hashMapOf("white spots" to "Ich", "red sores" to "hole disease")
  • const कीवर्ड का इस्तेमाल करके कंपाइल-टाइम कॉन्सटेंट तय करें. आप उन्हें शीर्ष स्तर पर रख सकते हैं, उन्हें एक टोन वाले ऑब्जेक्ट में व्यवस्थित कर सकते हैं या उन्हें एक साथी ऑब्जेक्ट में रख सकते हैं.
  • कंपैनियन ऑब्जेक्ट, क्लास की परिभाषा के अंदर एक सिंगलटन ऑब्जेक्ट होता है. इसके बारे में companion कीवर्ड से बताया जाता है.
  • एक्सटेंशन फ़ंक्शन और प्रॉपर्टी किसी क्लास में फ़ंक्शनैलिटी जोड़ सकती हैं. उदाहरण के लिए:
    fun String.hasSpaces() = find { it == ' ' } != null
  • अमान्य रिसीवर की मदद से आप किसी क्लास में null एक्सटेंशन बना सकते हैं. कोड चलाने से पहले, ?. ऑपरेटर को apply से जोड़ा जा सकता है, ताकि null की जांच की जा सके. उदाहरण के लिए:
    this?.apply { println("removing $this") }

Kotlin दस्तावेज़

अगर आपको इस कोर्स के किसी विषय के बारे में ज़्यादा जानकारी चाहिए या आपको कोई समस्या आती है, तो आप https://kotlinlang.org से शुरुआत कर सकते हैं.

Kotlin ट्यूटोरियल

https://try.kotlinlang.org वेबसाइट पर, Kotlin कोन्स नाम के रिच ट्यूटोरियल शामिल हैं, जो वेब पर आधारित अनुवादक है. साथ ही, इसमें रेफ़रंस दस्तावेज़ का पूरा सेट भी शामिल है, जिसमें उदाहरण भी दिए गए हैं.

Udcity कोर्स

इस विषय पर Udacity कोर्स देखने के लिए, प्रोग्रामर के लिए Kotlin बूटकैंप देखें.

IntelliJ IDEA

JetBrains वेबसाइट पर, InliJ IDEA के दस्तावेज़ देखे जा सकते हैं.

इस सेक्शन में उन छात्र-छात्राओं के लिए गृहकार्य की असाइनमेंट की सूची दी गई है जो इस कोडलैब के ज़रिए एक शिक्षक की देखरेख में कोर्स में काम कर रहे हैं. यह क्रिएटर का काम #33 पर निर्भर करता है:

  • अगर ज़रूरी हो, तो होमवर्क असाइन करें.
  • छात्र-छात्राओं को होमवर्क के असाइनमेंट सबमिट करने के तरीके के बारे में बताएं.
  • होमवर्क असाइनमेंट को ग्रेड दें.

शिक्षक इन सुझावों का इस्तेमाल जितनी चाहें उतनी कम या ज़्यादा कर सकते हैं. साथ ही, उन्हें अपने हिसाब से कोई भी होमवर्क असाइन करना चाहिए.

अगर आप इस कोडलैब के ज़रिए खुद काम कर रहे हैं, तो बेझिझक इन होमवर्क असाइनमेंट का इस्तेमाल करें.

इन सवालों के जवाब दें

पहला सवाल

इनमें से कौनसा विकल्प किसी सूची की एक कॉपी दिखाता है?

add()

remove()

reversed()

contains()

दूसरा सवाल

इनमें से कौनसा एक्सटेंशन फ़ंक्शन class AquariumPlant(val color: String, val size: Int, private val cost: Double, val leafy: Boolean) पर कंपाइल वाली गड़बड़ी देगा?

fun AquariumPlant.isRed() = color == "red"

fun AquariumPlant.isBig() = size > 45

fun AquariumPlant.isExpensive() = cost > 10.00

fun AquariumPlant.isNotLeafy() = leafy == false

तीसरा सवाल

इनमें से कौनसी कोई जगह नहीं है जहां आप const val के साथ कॉन्सटेंट तय कर सकते हैं?

फ़ाइल के सबसे ऊपर के लेवल पर ▢

सामान्य क्लास में ▢

सिंगलटन ऑब्जेक्ट में ▢

कंपैनियन ऑब्जेक्ट में ▢

अगले लेसन पर जाएं: 5.2 जेनेरिक

कोर्स के बारे में खास जानकारी पाने के लिए, दूसरे कोडलैब के लिंक के साथ-साथ, &kot;Kotlin बूटकैंपर के लिए प्रोग्राम: कोर्स में आपका स्वागत है.