邊打游戲邊學編程,是一種怎樣的體驗?
前言
hello,大家好,我是bigsai,好久不見,甚是想念!今天給大家介紹一個邊玩游戲邊學編程的網站。
在日常生活中,很多人喜歡玩游戲,因為游戲中有著對抗博弈、控制的喜悅,用靈魂指法完成一波靚麗的操作。
但實際上,你的按鍵都是對應代碼中一個個方法函數去執行操作,并且界面做到一個圖形變化渲染讓你感覺你控制的是這個圖形界面,所以我一直非常佩服做游戲開發的,感覺他們真的非常diao。
我們對代碼并沒有半點興趣因為寫代碼的過程枯燥無趣,完全需要腦子去抽象出一個頁面、執行邏輯,出錯的時候有很簡單的找了半天…… 輸出、debug各種方式去找問題。
對于咱們這種懶人來說,想要鍛煉自己編程能力、算法真的是進入一種畏難的無限死循環,希望要么簡單點、要么有趣點,寫的東西最好也能像有些開發那樣看得見,摸得著,學習別那么難。
這不,今天就發現了一個非常適合初、中級學者鍛煉自己編程的網站:codingame—一個邊玩游戲邊學編程的網站!
網站主頁為:https://www.codingame.com/start
網站介紹
我們在學習技術、學習算法的時候,都喜歡看一些圖將抽象內容具體化,甚至是如果有一些動圖如果能夠模擬一下程序執行邏輯之類的那就更受歡迎了,但是往往這類內容涉及到的底層非常多,并且優質的內容非常稀疏,但我今天推薦的這個網站真的是挺讓人驚喜的,網站進入的第一感覺就是:臥槽,這是小霸王嘛? 啥玩意啊。
一些小游戲動畫切換背景,看著codingame這個url你絲毫不會想到這個網站跟編程有啥任何關系,只會想到:
- 這到底是個啥?
- 谷歌翻譯一下看看……
注冊個賬號登錄之后才能顯示更多的內容,仔細看下背景右側還是有一些代碼的,還是有一些非常神秘的感覺。
登錄之后,左上角的practice可以進行一些練習,頁面會有各種難度的游戲問題,這些問題都有一個小的游戲背景、規則、考察點等待你去完成,比如easy難度的大部分都是字符串、哈希、循環控制這類問題,而mid難度的考察點更廣泛比如很多二分查找、bfs、圖論等等,如果英文不好可以借助翻譯中英對比著看(狗頭??舉手),對于hard難度的有興趣可以自行挑戰。
對于這里面的問題,有的是文本形式的,但是更多的是小游戲方式有動畫更加直觀。
還有一個非常重要的是,它支持多種編程語言,不管你是那種主流語言的愛好者,都可以暢想邊玩游戲邊學編程的快樂。
easy初體驗:ASCII的藝術
這里和大家一起體驗一下easy題怎么玩,我首先點進去的是一個叫ASCII Art的題.
地址為:https://www.codingame.com/ide/puzzle/ascii-art
剛進來就是一種黑色科技感十足,讀完題可能有些小伙伴很懵逼,這是啥玩意,這個程序又跟我們平常見得有點不一樣,不需要像力扣那樣完成整個方法,也不是和acm那種提交整個可執行代碼提交,這個程序它會事先聲明好一些內容你只需要在它提示的地方寫對應邏輯的代碼就可以了,并且所有的結果要打印出來。
但是細心的小伙伴會發現這個其實就是和我們日常的刷題很像很像,不就換個樣子嘛,沒啥不一樣的。
而這題的題意也很簡單,我口述一下(可能不標準):
在機場你經常看到這個牛pi的顯示屏:(圖片)
你有沒有問過自己,在一個好的舊終端上怎么顯示這個數字?(我怎么會難為我自己呢),我們有:用ASCII藝術。
ASCII 藝術允許您使用字符來表示。準確地說,在我們的例子中,這些形式是詞。例如,單詞“MANHATTAN”可以在 ASCII 藝術中顯示如下:
這個就有點似曾相識了,我也曾打印過大的0-9……
在看輸入輸出和其他要求
輸入
第 1 行:寬度L以 ASCII 藝術表示的字母。所有字母的寬度相同。
第 2 行:高度H以 ASCII 藝術表示的字母。所有字母的高度相同。
第 3行:待輸出的文本T,有n個ASCII字符組成。
后面幾行:字符串 ABCDEFGHIJKLMNOPQRSTUVWXYZ? 以 ASCII 藝術字(輸出到屏幕結果)表示。
輸出
文本 T在 ASCII 藝術中。
字符 a 到 z 在 ASCII 藝術中顯示為大寫的等效字符。
不在區間 [az] 或 [AZ] 中的字符將在 ASCII 藝術中顯示為問號。
問題分析:
這雖然是個簡單的問題,但是怎么分析呢?
對于給定的寬度L,和高度H,其實就是限定了每個字符在控制臺的大小,這個如何理解呢,舉個例子你就能明白。對于0來說,不同寬高的0可能長得樣子不一樣滴:
- # # # # # # # # # #
- # # # # # #
- # # # # # # #
- # # # #
- # # # # # # #
- 3*3 3*5 4*5
- 圓潤型 瘦長型 標準型
其實也就是限定寬高每個字符你可以迅速鎖定它的位置,存儲方面不用多想肯定是個二維的存儲(多個一維或者二維)。
在輸出的時候,根據字符計算 對應的位置,對應輸出就可以了,考慮到一些小白玩家還是可能不太明白,我貼上自己的????代碼,僅供參考:
- import java.util.*;
- import java.io.*;
- import java.math.*;
- /**
- * Auto-generated code below aims at helping you parse
- * the standard input according to the problem statement.
- **/
- class Solution {
- public static void main(String args[]) {
- Scanner in = new Scanner(System.in);
- int L = in.nextInt();//寬
- int H = in.nextInt();//高
- char ch[][]=new char[H][L];
- if (in.hasNextLine()) {
- in.nextLine();
- }
- String T = in.nextLine().toUpperCase();
- for (int i = 0; i < H; i++) {
- String ROW = in.nextLine();//輸入每一行
- ch[i]=ROW.toCharArray();//賦值給對應行
- }
- char value[][]=new char[H][T.length()*L];
- for(int i=0;i<T.length();i++){
- char temp=T.charAt(i);
- int index=temp-'A';
- if(index<0||index>26)
- index=26;//不是字母統統問號 ???
- for(int j=0;j<H;j++){
- for(int q=0;q<L;q++)
- {
- value[j][q+i*L]=ch[j][q+L*index];//賦值給待輸出結果
- }
- }
- }
- for(char tem[]:value){
- for(char temp:tem){
- System.out.print(temp);
- }
- System.out.println();
- }
- // Write an answer using System.out.println()
- // To debug: System.err.println("Debug messages...");
- //System.out.println("answer");
- }
- }
執行過程:
測試完提交即可。
mid初體驗二分
看完一個easy題,你可能覺得好像也沒啥哈,那行,咱們一起看個經典的mid題:
鏈接為:https://www.codingame.com/ide/puzzle/shadows-of-the-knight-episode-1
這個題具體要求大家可以自行到上面看看,但是大概的意思就是:
告訴你你在的區域長寬,告訴你你的初始點。
你的目標是最終走到某個終點,不告訴你具體坐標,只告訴你目標點在你當前點的方位(有八個方向)。你需要在N步之內走到目標節點位置上,每走一輪你都要輸出你當前點的位置。
看到這個問題還沒讀太懂的時候,上去就寫了個每次只走一步的代碼,結果遇到一個非常長的地圖結構那就GG了。
后來想了一下,告訴方位我們可以每次進行二分查找,并且壓縮所在區域的位置啊,也就是
遇到所有U方位的:說明地圖最底部在這個點之上
遇到所有D方位的:說明地圖最頂部在這個點之下
遇到所有L方位的:說明地圖最右側在這個點左面
遇到所有R方位的:說明地圖最左部在這個點有點
通過使用二分,將以前的O(n)時間復雜度降到O(logn)級別,基本上可以找到所有點了。
個人的代碼可以給大家伙一個小參考:
- import java.util.*;
- import java.io.*;
- import java.math.*;
- /**
- * Auto-generated code below aims at helping you parse
- * the standard input according to the problem statement.
- **/
- class Player {
- public static void main(String args[]) {
- Scanner in = new Scanner(System.in);
- int W = in.nextInt(); // width of the building.
- int H = in.nextInt(); // height of the building.
- int N = in.nextInt(); // maximum number of turns before game over.
- int X0 = in.nextInt();
- int Y0 = in.nextInt();
- int u=0,d=H,l=0,r=W;
- // game loop
- while (true) {
- String bombDir = in.next(); // the direction of the bombs from batman's current location (U, UR, R, DR, D, DL, L or UL)
- // Write an action using System.out.println()
- // To debug: System.err.println("Debug messages...");
- if(bombDir.contains("U")){
- d=Y0;
- Y0=((u+Y0)/2);
- }
- if(bombDir.contains("D")){
- u=Y0+1;
- Y0=((d+Y0)/2);
- }
- if(bombDir.contains("L")){
- r=X0;
- X0=((l+X0)/2);
- }
- if(bombDir.contains("R")){
- l=X0;
- X0=((r+X0)/2);
- }
- // the location of the next window Batman should jump to.
- System.out.println(X0+" "+Y0);
- }
- }
- }
查看測試案例結果為:
當然,對于每一個測試案例,你可以滾動滑看其中的測試中間每一輪對應的動畫,還是相當nice的。
這樣自己寫的代碼能夠可視化的看到每一步驟運行在圖像上的結果,就像打怪升級一樣,有點意思。
總結
對于這么一個網站,對初學者編程興趣的激發還是挺友好的,推薦三兩隊友一起打怪升級,也可舍友相互比拼,把這個題丟到寢室群里讓大伙一塊看看,看誰先做對。
當然網站內容比較豐富這里就不一一列舉了,大家有興趣的可以自行體驗,在編程領域這種網站其實相對還是非常稀疏的。
不過任何一個工具都要挑著選著用,可以找一些有挑戰但自己可以接受的問題去嘗試。玩玩體驗一下還是挺有趣的!
邊玩游戲,邊學編程的體驗很nice,就是讀題有點費勁!