ट्रैक
/
R
R
/
अभ्यास
/
ब्लैकजैक
ब्लैकजैक

ब्लैकजैक

सीखने का अभ्यास

परिचय

switch() फंक्शन if ... else if की लंबी श्रृंखला की जगह एक संक्षिप्त विकल्प हो सकता है। जिस वेरिएबल पर switch() काम करता है वह आमतौर पर एक स्ट्रिंग होता है, और ऐसी स्थिति में सिलेक्टर से कोट्स हटाए जा सकते हैं।

star <- function(type) {
  switch(type,
    M = , # will "fall through" if no value given
    K = "red dwarf",
    G = "Earth-like",
    "bigger star" # only correct for O,B,A,F
  )
}

> star("M")
[1] "red dwarf"

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

जब switch() character टाइप पर काम करता है, तो अंतिम वैल्यू एक डिफॉल्ट होती है, जैसा यहाँ है। पूर्णांक टाइप के साथ कोई डिफॉल्ट नहीं दिया जा सकता।

dplyr में फंक्शन

बेस R में switch काफी सीमित है: यह केवल एक ही इनपुट से ठीक-ठीक मिलान करता है। जब R पहली बार 1993 में जारी हुआ था तब यह ठीक लगता था, लेकिन आज के इस्तेमाल के लिए इसमें सुधार की ज़रूरत है।

Note

जैसा कि Conditionals कॉन्सेप्ट में बताया गया है, tidyverse पैकेजों का संग्रह बेस R की कार्यक्षमता को पूरक बनाने (और कभी-कभी उसकी जगह लेने) के लिए बनाया गया है, बिना बैकवर्ड कंपैटिबिलिटी पर असर डाले।

dplyr पैकेज को स्कोप में लाने के लिए अपने कोड के ऊपर library(dplyr) (केवल उस एक पैकेज के लिए) या library(tidyverse) (पूरे संग्रह के लिए) जोड़ दीजिए।

dplyr लाइब्रेरी switch से जुड़े दो अतिरिक्त फंक्शन देती है।

recode_values और replace_values फंक्शन

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

इन दोनों में मुख्य अंतर यह है कि recode_values() पूरी तरह नया वेक्टर बनाता है, जबकि replace_values() किसी मौजूदा वेक्टर को आंशिक रूप से बदलने देता है।

मिलान अब भी ठीक-ठीक ही होता है, लेकिन:

  • बाईं ओर के विकल्प वेक्टर हो सकते हैं, और अगर कोई भी एलिमेंट मिलता है तो इनपुट मिलान माना जाता है।
  • बाईं ओर के विकल्प और दाईं ओर के परिणाम = के बजाय टिल्ड ~ से जुड़े होते हैं।
  • हर स्थिति में एक डिफॉल्ट दिया जा सकता है।
library(dplyr)

x <- c("a", "b", "a", "d", "b", NA, "c", "e", "z")
recode_values(
  x,
  "a" ~ 1,
  "b" ~ 2,
  "c" ~ 3,
  c("d", "e") ~ 4, # either "d' or "e" will match
  NA ~ 0,          # matches missing values
  default = 100   # note the different syntax for the default
)
#> [1]   1   2   1   4   2   0   3   4 100

case_when फंक्शन

case_when case_match के सिंटैक्स को एक कदम और आगे ले जाता है, क्योंकि यह ~ के बाईं ओर किसी भी लॉजिकल एक्सप्रेशन की अनुमति देता है।

इनपुट वेक्टर (नीचे के उदाहरण में x) आर्गुमेंट के रूप में नहीं दिया जाता, उसका पहले से बना होना भर ज़रूरी है।

x <- 1:10
case_when(
  x < 3 ~ "low",
  between(x, 3, 5) ~ "mid",
  between(x, 6, 8) ~ "high",
  .default = "what?"
)
#>  [1] "low"   "low"   "mid"   "mid"   "mid"   "high"  "high"  "high"  "what?" "what?"

between() फंक्शन भी dplyr का ही हिस्सा है।

निर्देश

इस अभ्यास में हम ब्लैकजैक खेल की पहली बारी का अनुकरण करेंगे।

आपको दो पत्ते मिलेंगे और आप डीलर का खुला हुआ पत्ता देख पाएँगे। सभी पत्तों को एक स्ट्रिंग से दर्शाया जाता है, जैसे "ace", "king", "three", "two" आदि। हर पत्ते की वैल्यू इस प्रकार है:

पत्ता वैल्यू पत्ता वैल्यू
ace 11 eight 8
two 2 nine 9
three 3 ten 10
four 4 jack 10
five 5 queen 10
six 6 king 10
seven 7 other 0

ध्यान दें: आम तौर पर इक्के की वैल्यू 1 या 11 हो सकती है, लेकिन सरलता के लिए हम मान लेंगे कि इसकी वैल्यू केवल 11 ही हो सकती है।

आपके दो पत्तों और डीलर के पत्ते के आधार पर खेल की पहली बारी के लिए एक रणनीति होती है, जिसमें आपके पास ये विकल्प होते हैं:

  • रुकना (S)
  • नया पत्ता लेना (H)
  • पत्ते अलग करना (P)
  • अपने आप जीत जाना (W)

हालाँकि यह अभी सबसे अच्छी नहीं है, आप उस रणनीति का पालन करेंगे जिसे आपके दोस्त एलेक्स विकसित कर रहे हैं। वह रणनीति इस प्रकार है:

  • अगर आपके पास दो इक्के हों, तो आपको हमेशा उन्हें अलग करना चाहिए।
  • अगर आपके पास ब्लैकजैक है (दो पत्ते जिनका जोड़ 21 होता है), और डीलर के पास इक्का, कोई तस्वीर वाला पत्ता या दहला नहीं है, तो आप अपने आप जीत जाते हैं। अगर डीलर के पास इनमें से कोई पत्ता है, तो आपको रुकना होगा और दूसरे पत्ते के खुलने का इंतज़ार करना होगा।
  • अगर आपके पत्तों का जोड़ [17, 20] के बीच हो, तो आपको हमेशा रुकना चाहिए।
  • अगर आपके पत्तों का जोड़ [12, 16] के बीच हो, तो आपको हमेशा रुकना चाहिए, सिवाय इसके कि डीलर के पास 7 या उससे बड़ा पत्ता हो। ऐसी स्थिति में आपको हमेशा नया पत्ता लेना चाहिए।
  • अगर आपके पत्तों का जोड़ 11 या उससे कम हो, तो आपको हमेशा नया पत्ता लेना चाहिए।

1. किसी भी दिए गए पत्ते की वैल्यू निकालिए

किसी पत्ते की संख्यात्मक वैल्यू निकालने के लिए parse_card नाम का एक फंक्शन बनाइए:

parse_card("ace")
# => 11

2. पहली बारी के निर्णय का लॉजिक बनाइए

first_turn नाम का एक फंक्शन लिखिए जो ऊपर बताए गए निर्णय का लॉजिक लागू करता है:

first_turn(card1, card2, dealer_card)

अपेक्षित परिणामों के कुछ उदाहरण यहाँ दिए गए हैं:

first_turn("ace", "ace", "jack") == "P"
first_turn("ace", "king", "ace") == "S"
first_turn("five", "queen", "ace") == "H"
GitHub के ज़रिए संपादित करें यह लिंक एक नई विंडो या टैब में खुलता है
R Exercism

ब्लैकजैक शुरू करने के लिए तैयार हैं?

Exercism पर साइन अप कीजिए और R को 21 कॉन्सेप्ट111 अभ्यास तथा असली इंसानों से मिलने वाली मेंटरिंग के साथ सीखिए और उसमें महारत हासिल कीजिए, वह भी बिल्कुल मुफ्त।