CodeGym /Java Blog /यादृच्छिक /कोडजिमवरील खेळ विभाग: उपयुक्त सिद्धांत
John Squirrels
पातळी 41
San Francisco

कोडजिमवरील खेळ विभाग: उपयुक्त सिद्धांत

यादृच्छिक या ग्रुपमध्ये प्रकाशित केले
CodeGym वरील "गेम्स" विभागात , तुम्हाला असे रोमांचक प्रकल्प सापडतील ज्यात लोकप्रिय संगणक गेम लिहिणे समाविष्ट आहे. लोकप्रिय गेम 2048, Minesweeper, Snake आणि इतर गेमची तुमची स्वतःची आवृत्ती तयार करायची आहे? हे सोपं आहे. आम्ही गेम लेखन एका चरण-दर-चरण प्रक्रियेत बदलले आहे. कोडजिमवरील "गेम्स" विभाग: उपयुक्त सिद्धांत - १गेम डेव्हलपर म्हणून तुमच्या क्षमतेची चाचणी घेण्यासाठी, तुम्हाला प्रगत प्रोग्रामर असण्याची गरज नाही, परंतु Java ज्ञानाचा विशिष्ट संच आवश्यक आहे. येथे तुम्हाला गेम लेखनात उपयुक्त ठरेल अशी माहिती मिळेल .

1. वारसा

CodeGym गेम इंजिनसह कार्य करताना वारसा वापरणे समाविष्ट आहे. पण ते काय आहे हे तुम्हाला माहीत नसेल तर? एकीकडे, आपल्याला हा विषय समजून घेणे आवश्यक आहे: तो स्तर 11 मध्ये अभ्यासला जातो. दुसरीकडे, इंजिन विशेषत: अगदी सोप्यासाठी डिझाइन केले गेले होते, जेणेकरून आपण वारशाच्या वरवरच्या ज्ञानापासून दूर जाऊ शकता. तर वारसा म्हणजे काय? अगदी सोप्या भाषेत सांगायचे तर, वारसा हा दोन वर्गांमधील संबंध आहे. त्यापैकी एक पालक बनतो आणि दुसरा मूल (वंशज) बनतो. शिवाय, त्याचे वंशज आहेत हे पालक वर्गाला माहीतही नसावे. दुसऱ्या शब्दांत सांगायचे तर, वंशज असल्यामुळे त्याचा काही विशेष फायदा होत नाही. परंतु वारसा वंशजांना अनेक फायदे देतो. आणि सर्वात महत्वाचे म्हणजे पालक वर्गाचे सर्व चल आणि पद्धती वंशज मध्ये दिसतात जसे की पालक वर्गाचा कोड वंशज वर्गावर कॉपी केला होता. हे संपूर्णपणे अचूक वर्णन नाही, परंतु वारसा समजून घेण्यासाठी ते पुरेसे आहे. उदाहरण 1: सर्वात सोपा वारसा.

public class Parent {

}
चाइल्ड क्लास विस्तारित कीवर्ड वापरून पालक वर्गाचा वारसा घेतो .

public class Child extends Parent {

}
उदाहरण २: पॅरेंट क्लासचे व्हेरिएबल्स वापरणे.

public class Parent {

   public int age;
   public String name;
}
चाइल्ड क्लास पालक वर्गाचे वय आणि नाव व्हेरिएबल्स वापरू शकतो जसे की ते पालक वर्गात घोषित केले आहेत .

public class Child extends Parent {

   public void printInfo() {

     System.out.println(name+" "+age);
   }
}
उदाहरण 3: पालक वर्गाच्या पद्धती वापरणे.

public class Parent {

   public int age;
   public String name;

   public getName() {
      return name;
  }
}
चाइल्ड क्लास पॅरेंट क्लासचे व्हेरिएबल्स आणि पद्धती चाइल्ड क्लासमध्ये घोषित केल्याप्रमाणे वापरू शकतो . या उदाहरणात, आम्ही getName() पद्धत वापरतो.

public class Child extends Parent {

   public void printInfo() {

     System.out.println(getName()+" "+age);
   }
}
कंपाइलरला चाइल्ड क्लास असे दिसते:

public class Child extends Parent{

   public int age;  // Inherited variable
   public String name;  // Inherited variable

   public getName() {  // Inherited method.
      return name;
  }
   public void printInfo() {

     System.out.println(getName()+" "+age);
   }
}

2. ओव्हरराइडिंग पद्धती

काहीवेळा अशी परिस्थिती असते जेव्हा आम्ही आमच्या बाल वर्गाला काही अतिशय उपयुक्त पालक वर्ग, त्याच्या सर्व व्हेरिएबल्स आणि पद्धतींसह वारसा बनवतो, परंतु काही पद्धती आम्हाला पाहिजे त्याप्रमाणे कार्य करत नाहीत. किंवा आम्ही त्यांना कसे हवे आहे ते अजिबात नाही. या परिस्थितीत आपण काय करू शकतो? आम्हाला आवडत नसलेली पद्धत आम्ही ओव्हरराइड करू शकतो. हे करणे खूप सोपे आहे: आमच्या चाइल्ड क्लासमध्ये, आम्ही फक्त पॅरेंट क्लासमधील पद्धतीप्रमाणेच स्वाक्षरी असलेली पद्धत घोषित करतो आणि नंतर आम्ही त्यात आमचा स्वतःचा कोड लिहितो. उदाहरण १: पद्धत ओव्हरराइड करणे.

public class Parent {

   public String name;

   public void setName(String nameNew) {
       name = nameNew;
  }

   public getName() {
      return name;
  }
}
printInfo() पद्धत "Luke, No!!!" प्रदर्शित करेल.

public class Child extends Parent{

   public void setName(String nameNew) {
       name = nameNew + ", No!!!";
  }

   public void printInfo() {
      setName("Luke");
      System.out.println(getName());
   }
}
कंपाइलरला चाइल्ड क्लास असे दिसते:

public Child extends Parent {

   public String name;  // Inherited variable

   public void setName(String nameNew)  // Overridden method instead of the inherited method {

       name = nameNew + ", No!!!";
   }
   public getName() {  // Inherited method.

      return name;
   }
   public void printInfo() {

     setName("Luke");
     System.out.println( getName());
   }
}
उदाहरण 2: काही वारसा जादू (आणि पद्धत ओव्हरराइडिंग).

public class Parent {

   public getName() {
      return "Luke";
  }
   public void printInfo() {

     System.out.println(getName());
   }
}

public class Child extends Parent {

   public getName() {
      return "Luke, I am your father";
  }
}
या उदाहरणात, जर printInfoबाल वर्गात पद्धत (पालक वर्गातील) ओव्हरराइड केलेली नसेल, जेव्हा ही पद्धत चाइल्ड ऑब्जेक्टवर कॉल केली जाते, तेव्हा getName()पालक वर्गाच्या getName()पद्धतीऐवजी तिची पद्धत कॉल केली जाईल.

Parent parent = new Parent ();
parent.printnInfo();
हा कोड स्क्रीनवर "ल्यूक" प्रदर्शित करतो.

Child child = new Child ();
child.printnInfo();
हा कोड स्क्रीनवर "ल्यूक, मी तुझा पिता आहे" प्रदर्शित करतो.
कंपाइलरला चाइल्ड क्लास असे दिसते:

public class Child extends Parent {

   public getName() {
      return "Luke, I am your father";
   }
   public void printInfo() {

     System.out.println(getName());
   }
}

3. याद्या

आपण अद्याप याद्या (सूची) भेटल्या नसल्यास, येथे एक संक्षिप्त विहंगावलोकन आहे. तुम्ही CodeGym कोर्सच्या स्तर 6-7 मध्ये संपूर्ण माहिती मिळवू शकता . अ‍ॅरेसह सूचीमध्ये बरेच साम्य आहे:
  • आपण विशिष्ट प्रकारचा भरपूर डेटा संचयित करू शकता;
  • ते तुम्हाला त्यांच्या निर्देशांकानुसार वस्तू मिळवू देतात;
  • घटक निर्देशांक 0 पासून सुरू होतात.
याद्यांचे फायदे: अॅरेच्या विपरीत, याद्या गतिमानपणे आकार बदलू शकतात. जेव्हा एखादी सूची तयार केली जाते, तेव्हा तिचा आकार 0 असतो. तुम्ही सूचीमध्ये आयटम जोडताच, त्याचा आकार वाढतो. येथे सूची तयार करण्याचे उदाहरण आहे:

ArrayList<String> myList = new ArrayList<String>(); // Create a new ArrayList
कोन कंसातील मूल्य सूची संचयित करू शकणारा डेटा प्रकार दर्शवते. सूचीसह कार्य करण्यासाठी येथे काही पद्धती आहेत:
कोड कोड काय करतो याचे संक्षिप्त वर्णन
ArrayList<String> list = new ArrayList<String>(); स्ट्रिंगची नवीन यादी तयार करा
list.add("name"); सूचीच्या शेवटी एक घटक जोडा
list.add(0, "name"); सूचीच्या सुरुवातीला एक घटक जोडा
String name = list.get(5); त्याच्या निर्देशांकानुसार घटक मिळवा
list.set(5, "new name"); घटक त्याच्या निर्देशांकानुसार बदला
int count = list.size(); सूचीतील घटकांची संख्या मिळवा
list.remove(4); सूचीमधून एक घटक हटवा
तुम्ही खालील लेखांमधून सूचींबद्दल अधिक जाणून घेऊ शकता:
  1. ArrayList वर्ग
  2. चित्रांमध्ये अॅरेलिस्ट
  3. ArrayList मधून घटक हटवत आहे

4. अॅरे

मॅट्रिक्स म्हणजे काय? मॅट्रिक्स हे आयताकृती सारणीपेक्षा अधिक काही नाही जे डेटाने भरले जाऊ शकते. दुसऱ्या शब्दांत, तो द्विमितीय अॅरे आहे. तुम्हाला माहीत असेलच, Java मधील अॅरे हे ऑब्जेक्ट्स आहेत. एक मानक एक-आयामी intअॅरे यासारखे दिसते:

int [] array = {12, 32, 43, 54, 15, 36, 67, 28};
आम्ही हे असे दृश्यमान करू शकतो:
0 2 3 4 6
१२ 32 ४३ ५४ १५ ३६ ६७ २८
शीर्ष पंक्ती सेलचे पत्ते दर्शवते. दुसऱ्या शब्दांत, क्रमांक 67 मिळविण्यासाठी, तुम्हाला अनुक्रमणिका 6 सह अॅरे घटकात प्रवेश करणे आवश्यक आहे:

int number = array[6];
हे सर्व खूप सोपे आहे. द्विमितीय अॅरे म्हणजे एक-आयामी अॅरेचा अॅरे. जर तुम्ही याबद्दल पहिल्यांदाच ऐकत असाल, तर थांबा आणि तुमच्या डोक्यात याची कल्पना करा. द्विमितीय अॅरे असे दिसते:
0 एक - मितीय अॅरे एक-आयामी अॅरे
एक-आयामी अॅरे
2 एक-आयामी अॅरे
3 एक-आयामी अॅरे
4 एक-आयामी अॅरे
एक-आयामी अॅरे
6 एक-आयामी अॅरे
एक-आयामी अॅरे
कोडमध्ये:

int [][] matrix = {
{65, 99, 87, 90, 156, 75, 98, 78}, {76, 15, 76, 91, 66, 90, 15, 77}, {65, 96, 17, 25, 36, 75, 54, 78}, {59, 45, 68, 14, 57, 1, 9, 63}, {81, 74, 47, 52, 42, 785, 56, 96}, {66, 74, 58, 16, 98, 140, 55, 77}, {120, 99, 13, 90, 78, 98, 14, 78}, {20, 18, 74, 91, 96, 104, 105, 77} }
0 0 2 3 4 6
६५ ९९ ८७ 90 १५६ 75 ९८ ७८
0 2 3 4 6
७६ १५ ७६ ९१ ६६ 90 १५ ७७
2 0 2 3 4 6
६५ ९६ १७ २५ ३६ 75 ५४ ७८
3 0 2 3 4 6
५९ ४५ ६८ 14 ५७ ६३
4 0 2 3 4 6
८१ ७४ ४७ 52 42 ७८५ ५६ ९६
0 2 3 4 6
६६ ७४ ५८ 16 ९८ 140 ५५ ७७
6 0 2 3 4 6
120 ९९ 13 90 ७८ ९८ 14 ७८
0 2 3 4 6
20 १८ ७४ ९१ ९६ 104 105 ७७
मूल्य 47 मिळविण्यासाठी, तुम्हाला [4][2] येथे मॅट्रिक्स घटकाचा संदर्भ घ्यावा लागेल.

int number = matrix[4][2];
तुमच्या लक्षात आले असेल की मॅट्रिक्स निर्देशांक शास्त्रीय आयताकृती समन्वय प्रणाली (कार्टेशियन समन्वय प्रणाली) पेक्षा वेगळे आहेत. जेव्हा तुम्ही मॅट्रिक्समध्ये प्रवेश करता, तेव्हा तुम्ही प्रथम y निर्देशांक आणि नंतर x निर्देशांक निर्दिष्ट करता. गणितात, प्रथम x निर्देशांक निर्दिष्ट करण्याची प्रथा आहे, म्हणजे (x, y). तुम्ही कदाचित विचार करत असाल: "बरं, मॅट्रिक्सचे तुमचे प्रतिनिधित्व का फिरवू नये आणि नंतर (x, y) वापरून नेहमीच्या पद्धतीने घटकांमध्ये प्रवेश का करू नये? असे केल्याने मॅट्रिक्सची सामग्री बदलणार नाही". होय, काहीही बदलणार नाही. परंतु प्रोग्रामिंग जगामध्ये, "प्रथम y, नंतर x" मॅट्रिक्समध्ये प्रवेश करणे ही स्वीकृत प्रथा आहे. आपण हे योग्य मार्ग म्हणून स्वीकारले पाहिजे. आता आपल्या इंजिनमध्ये मॅट्रिक्स प्रक्षेपित करण्याबद्दल बोलूया (Gameवर्ग). आपल्याला माहिती आहे की, इंजिनमध्ये अनेक पद्धती आहेत ज्या विशिष्ट निर्देशांकांवर खेळण्याच्या क्षेत्राच्या पेशी बदलतात. उदाहरणार्थ, setCellValue(int x, int y, String value)पद्धत. हे मूल्य पॅरामीटरच्या समान निर्देशांक (x, y) सह विशिष्ट सेल सेट करते. तुमच्या लक्षात आले असेल की शास्त्रीय समन्वय प्रणालीप्रमाणेच ही पद्धत प्रथम x घेते. इंजिनच्या इतर पद्धती अशाच प्रकारे कार्य करतात. गेम विकसित करताना, स्क्रीनवर मॅट्रिक्सची स्थिती पुनरुत्पादित करणे आवश्यक असते. आम्ही ते कसे करू? प्रथम, तुम्हाला लूपमधील सर्व मॅट्रिक्स घटकांमधून पुनरावृत्ती करणे आवश्यक आहे. दुसरे, रिव्हर्सेड कोऑर्डिनेट्स वापरून त्या प्रत्येकासाठी डिस्प्ले पद्धत कॉल करा. उदाहरणार्थ:

private void drawScene() {
    for (int i = 0; i < matrix.length; i++) {
        for (int j = 0; j < matrix[i].length; j++) {
            setCellValue(j, i, String.valueOf(matrix[i][j]));
        }
    }
}
साहजिकच, रिव्हर्सल दोन्ही दिशांनी कार्य करते. तुम्ही पद्धतीमध्ये (i, j) पास करू शकता setCellValueआणि एकाच वेळी मॅट्रिक्समधून [j][i] घटक घेऊ शकता. निर्देशांक उलट करणे थोडे कठीण वाटू शकते, परंतु तुम्हाला ते लक्षात ठेवणे आवश्यक आहे. आणि नेहमी, तुम्हाला काही समस्या आल्यास, तुम्ही कागदाचा तुकडा आणि पेन घ्या, मॅट्रिक्स काढा आणि मॅट्रिक्सचा समावेश असलेल्या प्रक्रियांचे पुनरुत्पादन करा.

5. यादृच्छिक संख्या

तुम्ही यादृच्छिक क्रमांक जनरेटरसह कसे कार्य कराल? वर्ग पद्धत Gameपरिभाषित करतो getRandomNumber(int). हुड अंतर्गत, ते Randomjava.util पॅकेजमधील वर्ग वापरते, परंतु तुम्ही यादृच्छिक क्रमांक जनरेटरसह कार्य करण्याची पद्धत बदलत नाही. getRandomNumber(int)युक्तिवाद म्हणून पूर्णांक घेते. जनरेटर काय परत करू शकतो यावर ही संख्या वरची मर्यादा असेल. खालची मर्यादा 0 आहे. महत्वाचे! जनरेटर कधीही वरची मर्यादा क्रमांक परत करणार नाही. उदाहरणार्थ, तुम्ही कॉल केल्यास getRandomNumber(3), ते यादृच्छिकपणे 0, 1, किंवा 2 परत करेल. तुम्ही बघू शकता, ते 3 परत करू शकत नाही. अशा प्रकारे जनरेटर वापरणे अगदी सोपे आहे, परंतु बर्याच बाबतीत अत्यंत प्रभावी आहे. समजा तुम्हाला काही श्रेणीमध्ये एक यादृच्छिक क्रमांक मिळवण्याची आवश्यकता आहे: कल्पना करा की तुम्हाला श्रेणी [100..999] मध्ये तीन-अंकी संख्या आवश्यक आहे. तुम्हाला आधीच माहित आहे की, परत केलेली किमान संख्या 0 आहे. त्यामुळे तुम्हाला 100 जोडणे आवश्यक आहे. परंतु या प्रकरणात, तुम्ही वरची मर्यादा ओलांडणार नाही याची काळजी घेणे आवश्यक आहे. कमाल यादृच्छिक मूल्य म्हणून 999 मिळवण्यासाठी, कॉल कराgetRandomNumber(int)वितर्क 1000 सह पद्धत. परंतु आता आम्हाला आठवते की आम्ही निकालात 100 जोडत आहोत: याचा अर्थ असा आहे की वरची सीमा 100 ने कमी केली पाहिजे. दुसऱ्या शब्दांत, आमची यादृच्छिक तीन-अंकी संख्या मिळविण्याचा कोड यासारखा दिसेल :

int number = 100 + getRandomNumber(900);
परंतु ही प्रक्रिया सुलभ करण्यासाठी, इंजिन अशी getRandomNumber(int, int)पद्धत प्रदान करते ज्याचा पहिला पॅरामीटर परत करण्यासाठी किमान संख्या आहे. या पद्धतीचा वापर करून, मागील उदाहरण खालीलप्रमाणे पुन्हा लिहिले जाऊ शकते:

int number = getRandomNumber(100, 1000);
यादृच्छिक अॅरे घटक मिळविण्यासाठी यादृच्छिक संख्या वापरल्या जाऊ शकतात:

String [] names = {"Sarah", "Val", "Sergey"};
String randomName = names[getRandomNumber(names.length)]
काही संभाव्यतेसह काही घटना निर्माण करणे. मानवांसाठी, सकाळची सुरुवात काही संभाव्य परिस्थितींनी होते: जास्त झोपणे - 50% शक्यता; वेळेवर जागे झाले - 40% शक्यता; एक तास लवकर उठलो - 10% शक्यता. कल्पना करा की तुम्ही सकाळचा परिणाम जनरेटर लिहित आहात. तुम्हाला एका विशिष्ट संभाव्यतेसह इव्हेंट व्युत्पन्न करणे आवश्यक आहे. हे करण्यासाठी, आपल्याला पुन्हा यादृच्छिक क्रमांक जनरेटर वापरण्याची आवश्यकता आहे. भिन्न अंमलबजावणी शक्य आहे, परंतु सर्वात सोपी खालील अल्गोरिदमवर आधारित असावी:
  1. संख्या व्युत्पन्न करण्यासाठी वापरलेल्या मर्यादा सेट करा;
  2. एक यादृच्छिक संख्या व्युत्पन्न करा;
  3. प्राप्त क्रमांकावर प्रक्रिया करा.
या प्रकरणात, कमाल 10 असेल. कॉल कराgetRandomNumber(10)पद्धत आणि विश्लेषण करा की आम्ही ते परत करू शकतो. हे 10 संख्या (0 ते 9 पर्यंत) परत करू शकते, प्रत्येक समान संभाव्यतेसह - 10%. आता आम्हाला सर्व संभाव्य परिणाम एकत्र करणे आणि त्यांना आमच्या संभाव्य घटनांमध्ये मॅप करणे आवश्यक आहे. तुमची कल्पनाशक्ती अनेक संभाव्य संयोजनांचा विचार करू शकते, परंतु येथे सर्वात स्पष्ट आहे: "जर यादृच्छिक संख्या श्रेणी [0..4] मध्ये असेल, तर आमच्याकडे "ओव्हरस्लीप्ट" इव्हेंट आहे; जर संख्या [5] श्रेणीत असेल ..8], आमच्याकडे "वेक अप वेळेवर" इव्हेंट आहे; आणि जर संख्या 9 असेल, तर आमच्याकडे "एक तास लवकर जागे व्हा" इव्हेंट आहे. हे सर्व अगदी सोपे आहे. रेंजमध्ये 5 संख्या आहेत [0 ..4], त्यापैकी प्रत्येक 10% च्या संभाव्यतेसह, एकूण 50% साठी परत केला जाऊ शकतो; रेंजमध्ये 4 संख्या आहेत [5..8], तसेच, आणि 9 ही फक्त एक संख्या आहे जी यासह दिसते 10% ची संभाव्यता.

int randomNumber = getRandomNumber(10);
if (randomNumber < 5) {
    System.out.println("Overslept");
} else if (randomNumber < 9) {
    System.out.println("Woke up on time");
} else {
    System.out.println("Woke up an hour early");
}
सर्वसाधारणपणे, यादृच्छिक संख्या वापरण्याचे बरेच मार्ग आहेत. तुम्ही फक्त तुमच्या कल्पनेने मर्यादित आहात. परंतु आपल्याला वारंवार काही परिणाम प्राप्त करण्याची आवश्यकता असल्यास ते सर्वात प्रभावीपणे वापरले जातात. मग नवीन निकाल मागील निकालापेक्षा वेगळा असेल. काही संभाव्यतेसह, अर्थातच. आतासाठी एवढेच! तुम्हाला "गेम" विभागाबद्दल अधिक जाणून घ्यायचे असल्यास, येथे काही उपयुक्त दस्तऐवज आहेत जे मदत करू शकतात:
टिप्पण्या
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION