دوشنبه، اسفند ۰۳، ۱۳۸۸

کد بازی دوز - ویژوال بیسیک Tic TacToe - XO

بسم الله الرحمن الرحیم
سلام.
این وبلاگ هم مثل خودمه. کم بازدید.
اینجا یه جورایی شده مثل دفترچه خاطرات من . بازار سید اسماعیل
به هر حال
2 شب پیش داشتم روی این فکر می کردم که بازی دوز، همون XO یا Tic Tac Toe رو به چه شکل میشه نرم افزاری شبیه سازی کرد.
دوزبازهای حرفه ای مثل شما میدونند که این بازی یک نکته ساده داره:
شما هرگز برنده نمی شوید مگر اینکه حریف خانه ای را به اشتباه انتخاب کند.سوتی(صوتی) بدهد! پس اگر بازیکن ها اشتباه نکنند، بازی برنده نخواهد داشت.

و همون دوزباز اگر خیلی هنرمند باشه اینها رو میدونه:

1- اگر حرکت اول با حریف بود، باید اولین انتخاب بگونه ای باشه که در حرکات بعدی 2 راهه نشین. واگر اولین خونه رو اشتباه بزنین و حریف عقل سالم داشته باشه، بازی رو خواهید باخت.

2- اگرنوبت اول با شما بود بود، تمام خانه ها شانس دوراهه کردن رو برای شما فراهم میکنند فقط باید منتظر اشتباه حریف باشید.

صرف نظر از تجربه ی عمیق بنده در دووز(!)، برنامه ای که در زیر تقدیم میشود، با استفاده از هوش مصنوعی، بهترین خانه برای جلوگیری از 2 راهه شدن رو به ما معرفی میکنه.
این مثال 2راهه شدنه:
نوبت با o
در اینجا x برنده است. چون اگرo در پایین یا وسط علامت بزنه، نوبت دوباره به x میرسه و x هنوز یک خط دیگه برای کامل کردن داره.
حالا چی شد که اینطوری شد؟

روی کاغذ امتحان کنید.
x اولین حرکت رو داره و پایین راست رو انتخاب میکنه.
o بالا چت رو انتخاب میکنه.
x بالا راست،
و حالا o چاره ای نداره جز اینکه راست رو انتخاب کنه و الا باخته.
حالا x پایین چپ رو میزنه و به این ترتیب میرسه به جایی که در تصویر بالا نظاره گر بودید.o دوراهه شده و باخته.

روی یک برگه این رو امتحان کنید.
حرکت اول با x و انتخاب، همون پایین راست باشه.
o اگر
هر جایی به جز وسط بزنه، بازی رو خواهد باخت!
پس معلوم شد در این حالت وسط ارزشمند ترینه. ارزشش هم به اینه که بازی نهایتا بدون برنده باشه.
حالا ما میتونیم به برنامه بگیم هروقت کاربر گوشه زد، شما وسط رو بزن( چون از قبل میدونیم). اما اینجوری حال نمیده! باید برنامه خودش درک و شعور داشته باشه!
کل کار رو الگرویتم AI انجام میده به نام MiniMax کارش اینه که تا چند مرحله ی بعد، تمامی حرکات ممکن برای هر دو بازیکن رو خودش یک بار انجام بده، و برای هر حرکت یک امتیاز در نظر بگیره.با توجه به امتیاز ها، در هر مرحله در طول شیبه سازی بازی، برای حریف بدترین حالت و برای خودش بهترین حالت رو در نظر میگیره. و هیچ کاری به احتمالات نداره.
اینطور فرض میشه که حریف انتخاب هایی رو بکنه که خودش رو به برد نزدیک و یا از باخت خودش جلوگیری کنه. ما این انتخاب ها رو از حریف میگیریم چطوری؟ دست حریف رو برای انتخاب های آزاد میبندیم. به طور مثال برنامه اینطوری حساب میکنه که اگر بعد از اینکه حریف گوشه رو زد، وسط رو نزنه- با فرض اینکه حریف ایده آل باشه- در ادامه دوراهه خواهد شد. بنابراین، برنامه وسط رو برای خودش انتخاب میکنه چون در این صورت، حریف دیگه راهی برای دوراهه کرن نداره.
اما امتیاز دهی به چه صورت هست. یه بررسی کردم دیدم معمولا امتیاز دهی به این صورت هست که به جای امتیاز به حرکات، به خانه ها امتیاز میدن
مثلا، اگر 2 تا x در یک خط قرار بگیره، به حرکتی که منجر به این حالت بشه +10 و اگر 2 تا o در یک سطر قرار بگیره برای حرکتی که منتهی به این حالت بشه، امتیاز -10 (یعنی به اندازه ی 10 تا ارزشمند برای حریف) تعلق میگیره.
حالا اگر 3 تا o در یک سطر داشته باشیم، امتیاز -100 به حرکت قبلی حریف تعلق میگیره. و برنامه اینطور فرض میکنه که حریف بین -100 و -10 ، -100 رو انتخاب کنه.یعنی بدترین حالت برای ما.پس مقدار -100 نتیجه ی یکی از حرکات برنامه است که برنامه از انجام اون حرکت که این امتیاز بزرگ رو برای کاربر داشته باشه اجتناب میکنه.
اما من یه کار دیگه کردم
به هر حرکت با توجه به عمقی که داره، امتیاز تعلق دادم. و ملاکم برای امتیاز دهی برخلاف الگوریتم توضیح داده شده وضعیت کل صفحه ی بازی نبود.صرفا؛ مجموع امتیاز های به دست آمده به توجه به عمق حرکت و نتیجه ی حاصله( پیروزی کاربر، پیروزی برنامه و بدون برنده) مد نظر هست.

و بله،این برنامه شکست ناپذیره...
در کد برنامه سعی کردم توضیحات به اندازه ی کافی بنویسم.

دانلود کد

خوشحال میشم نظرتون رو ببینم.
خداحافظ