[Hexschool JS60 Training] — 60天 JavaScript 學徒試煉 Day1-30

60天特訓

Introduction & 前言

結束八週切版直播版,接著 六角學院 開了一門關於 JavaScript(下稱JS) 的新課程。

雖然筆者沒有報名參加,但是 六角學院 為了銜接上課程舉辦了為期 60天的 JS 學徒試煉

這篇文章將紀錄 60天的練習,自己也會出一些新的題目,有興趣的朋友們也可以試著解題,或是在下方留言一起討論。

這篇文章將會記錄第 1 天 - 30 天 的練習。


Summary & 摘要

每天早上校長會出一題關於 JS 的題目,這邊將會記錄下來自己的解題過程,自己也可能會提出新的題目,有解出題目答案或是不了解也可以在下方留言一起討論,如果題目出得不好也請各路大神手下留情。


每日題目

Day1

第一天是關於 JS 宣告的練習。

第一天的練習

解題關鍵:由於 var 在創造階段會先被提升到頂部,所以通常有經過宣告的變數在還沒賦值的情況下 console.log 都會拿到 undefined;有興趣了解基本原理可參考 [JavaScript Notes] — 淺談 JavaScript #1

Day2

第二天六角的題目:

請依照以下房型資訊,去定義各個變數名稱,變數務必要命名比較語意化且好懂。

第一天的練習

第二天六角題目解答:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
// 1. 採用小駝峰命名
// 2. 房間的設定都包在 singleRoom 裡, 這樣可以減少命名重複
// 如果有其他的房間設定, 就可以再包一個 例: var doubleRoom = { ...略 }

var singleRoom = {
peopleLimit: 1, // (人數限制)Number
bedSize: '單人床', // (床型)String
bathroomNum: 1, // (廁所數量)Number
feetSize: 18, // (房間大小)Number
sizeType: '平方公尺', // (房間大小單位)String
description: 'Single Room is only...', // (房間描述)String
checkInTimeFrom: '15:00', // (CheckIn時間, 起始時間)String
checkInTimeTo: '21:00', // (CheckIn時間, 結束時間)String
checkOutTimeFrom: '10:00', // (CheckOut時間, 起始時間)String
checkOutTimeTo: '21:00', // (CheckOut時間, 結束時間)String
feature: {
wifi: true, // (無線網路)Boolean
landlinePhone: true, // (室內電話)Boolean
breakfast: true, // (早餐)Boolean
airConditioning: true, // (空調)Boolean
miniBar: false, // (酒吧))Boolean
refrigerator: true // (冰箱)Boolean
}, // (房間特徵/設備)Object
} // (單人房)Object

解題關鍵:變數命名務必好懂為主,且 第一個字元不允許是數字,不允許包含空格和其他標點符號!另外變數 名區分大小寫,允許包含字母、數字、美元符號($)和下劃線,但是通常開頭不會使用 美元符號($)和下劃線,第一個字以後也會盡量避免,所以通常推薦使用駝峰命名法

第二天自己的題目為:

第二天自己的題目

Day3

第三天六角的題目為:

第一題 - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
8
9
10
11
12
var a = 1;
console.log(typeof(a));

var b = "hello";
console.log(typeof(b));

var c = 1+"hello";
console.log(typeof(c));

var d = 1+"11";
console.log(d)
console.log(typeof(d))

第二題 - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
var a;
a = a+"hello"
console.log(a);
console.log(typeof(a))

var b = 3;
console.log(b*"hello");

第三題 - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
var a = 9;
console.log(a+9);
console.log(a+'9');

var b = "9";
console.log(b*b)
console.log(typeof(b*b))

第二天六角題目解答:

第一題解答

1
2
3
4
5
6
7
8
9
10
11
12
var a = 1;
console.log(typeof(a)); // Number

var b = "hello";
console.log(typeof(b)); // String

var c = 1+"hello";
console.log(typeof(c)); // String

var d = 1+"11";
console.log(d) // 111
console.log(typeof(d)) // String

第二題解答

1
2
3
4
5
6
7
var a;
a = a+"hello"
console.log(a); // undefinedhello
console.log(typeof(a)) // String

var b = 3;
console.log(b*"hello"); // NaN

第三題解答

1
2
3
4
5
6
7
var a = 9;
console.log(a+9); // 18
console.log(a+'9'); // 99

var b = "9";
console.log(b*b) // 81
console.log(typeof(b*b)) // Number

解題關鍵:注意型別轉換,通常 數字字串,最容易發生轉換後的問題,還有小數點相加等於的問題,有興趣可參考 Kuro Hsu 大大的 重新認識 JavaScript: Day 03 變數與資料型別

第三天自己的題目為:

請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
8
9
var a = 'a';

console.log(a*10);
console.log(typeof a);

var b = 'ba';

console.log(b+(+a)+a);
console.log(typeof (a*10));

解答為:

1
2
3
4
5
6
7
8
9
var a = 'a';

console.log(a*10); // NaN
console.log(typeof a); // String

var b = 'ba';

console.log(b+(+a)+a); // baNaNa
console.log(typeof (a*10)); // Number

這題上半部應該還算簡單,下半部是之前在某文章看到的有趣題目,console.log 出來會是香蕉😂。

比較陷阱大概是最下面的 console.log(typeof (a*10));,因為 JSconsole.log(NaN) 會出現 Number,如果真的要檢查 NaN 的型別,可以使用 isNaN(),詳細可參考**MDN**。

Day4

第四天六角的題目為:

第一題 - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var a = 1;
var b = 1;
console.log(a>0);
console.log((a+b)>1);

var c = 2;
var d = 3;
console.log(c == d);

var e = 4;
var f = 5;
console.log(f >= e);
console.log(f != e);
console.log(f == e);

第二題(搭配型別自動轉型) - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
7
8
9
var a=1; 
var b="1";
console.log(a==1);
console.log(a==b);

var c = 2;
var d = "3";
// 請解釋為什麼
console.log((c*d)>=5);

第三題(嚴謹模式) - 請依序告知以下 console.log 會顯示什麼值。

1
2
3
4
5
6
var a = 1;
var b = "1";
console.log(a==1);
console.log(a==b);
console.log(a===b);
console.log(a!==b);

第四天六角題目解答:

第一題解答

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var a = 1;
var b = 1;
console.log(a>0); // true
console.log((a+b)>1); // true

var c = 2;
var d = 3;
console.log(c == d); // false

var e = 4;
var f = 5;
console.log(f >= e); // true
console.log(f != e); // true
console.log(f == e); // false

第二題解答

1
2
3
4
5
6
7
8
9
10
var a=1; 
var b="1";
console.log(a==1); // true
console.log(a==b); // true

var c = 2;
var d = "3";
// Q:請解釋為什麼
// A:c*d 已經轉型為 Number, 6 大於等於 5 是對的
console.log((c*d)>=5); // true

第三題解答

1
2
3
4
5
6
var a = 1;
var b = "1";
console.log(a==1); // true
console.log(a==b); // true
console.log(a===b); // false
console.log(a!==b); // true

解題關鍵:需要再度注意型別轉換,某些情況下需要先轉型後在做計算,或是轉型後在做比對,而兩個 “=” 和三個是不同的,這是需要特別注意的,另外再複習一下昨日的關鍵,NaNNumber,如果真的要檢查需要使用 isNaN(),但通常會了避免出現 NaN 在計算前會先透過 number() 或是 parseInt() 去把字串轉為數字,只是為了保險起見還是需要確保傳進來的值都是 Number 才是最重要的!

Day5

第五天六角的題目為:

第一題 - 顧客 Bob 向店員詢價

顧客 Bob:「請問我要買 4 個漢堡,30 份薯條,總共多少?」

1
2
3
4
5
6
7
8
9
10
// 定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var bobTotal;

// 請將 Code 寫在這,運算內容賦予到 bobTotal,
// 並要利用到 hamburgerPrice、friesPrice
// 算出 Bob 的提問。

console.log( "Bob 您好,您詢問的金額總計為"+bobTotal+"元");

第二題 - 錢包剩下多少錢

mark 錢包裡有 200 元,買了一個漢堡,三個薯條,他還剩下多少錢?

1
2
3
4
5
6
7
8
9
10
11
// 定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var markWallet = 200;
var markTotal;

// 請將 Code 寫在這,運算内容賦予到 markTotal,
// 並要利用到 markWallet、hamburgerPrice、friesPrice
// 算出 mark 購買後剩餘的金額。

console.log('馬克買完東西後,錢包剩下'+markTotal +'元')

第三題 - 錢包剩下多少錢

顧客 Mary 身上有 5000 元,想要買 10 份漢堡、10 份薯條,因為他有會員卡,所以可以打九折優惠,請問他還剩下多少錢?

1
2
3
4
5
6
7
8
9
10
11
12
// 定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var sale = 0.9;
var maryWallet = 5000
var maryTotal;

// 請將 Code寫在這,運算內容賦予到 maryTotal ,
// 並要利用到hamburgerPrice、friesPrice、sale、maryWallet
// 算出 maryTotal 剩下的錢。

console.log( 'Mary 買完東西後,錢包剩下'+ maryTotal +'元')

第五天六角題目解答:

第一題

1
2
3
bobTotal = (4 * hamburgerPrice) + (30 * friesPrice); // 1400

console.log( "Bob 您好,您詢問的金額總計為 1400 元");

第二題

1
2
3
markTotal = markWallet - (hamburgerPrice + (3 * friesPrice)); // 30

console.log("馬克買完東西後,錢包剩下 30 元")

第三題

1
2
3
maryTotal = maryWallet - ((10 * hamburgerPrice) + (10 * friesPrice)) * sale; // 4190

console.log( 'Mary 買完東西後,錢包剩下 4190 元')

解題關鍵:本日需要注意加減乘除的運算權重,如果同樣權重的但是有區分先後,建議用括號刮起來,如果不確定,可以向本日筆者解題一樣,把需要一起先算的地方,先一起括號起來

Day6

第六天六角的題目為:

第一題 - 布林與比較運算子練習

成為 VIP 會員的條件,只要購買滿 200 元,就可無條件成為會員,Bob 買了 2 個漢堡,2 個 薯條,是否有滿足條件?

1
2
3
4
5
6
7
8
9
10
var VIPTotal = 200;
var hamburgerPrice = 50;
var friesPrice = 30;
var isVIP;

// 請透過比較運算子,將比較結果寫在isVip 上
// 請利用 VIPTotal、hamburgerPrice、friesPrice 的變數進行比較
// isVIP 的型別必須為布林值(true or false)

console.log("Bob的 VIP 條件為"+isVIP)

第二題 - 三心二意的老闆希望用邏輯運算子 &&

老闆發現大家都只買薯條衝 VIP 資格,導致大家都不買漢堡,老闆好生氣,他認為他的美味蟹堡是全美最好吃的,小杰也不知道他的自信從哪裡來的。

所以他跟小杰說,從今天起,VIP 條件必須同時符合以下兩點,才能成為 VIP 資格。

  1. 一次消費滿 200 元
  2. 一定要買 1 個漢堡

這時又來了兩位顧客,Mary 與 Mark,來看看他們有沒有符合條件吧!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
// 此變數不可更改
var VIPTotal = 200;
var hamburgerPrice = 50;
var friesprice = 30;
var markHamburgerNum = 2;
var markfriesNum = 4;
var markIsVIP;

// 如上面新增的變數,馬克買了2個漢堡,與4個薯條
// 請同時運用比較運算子與邏輯運算子,將比較結果寫在 markIsVIP 上
// markIsVIP 的型別必須為布林值(true or false)

console.log("mark的 VIP 條件為"+ markIsVIP)

var maryHamburgerNum = 0;
var maryfriesNum = 10;
var maryIsVIP;

// 如上面新增的變數,Mary買了0個漢堡,與10個薯條
// 請同時運用比較運算子與邏輯運算子,將比較結果寫在 markIsVIP 上
// maryIsVIP 的型別必須為布林值(true or false)

console.log("mary的 VIP 條件為"+ maryIsVIP)

第三題 - Mary 很生氣,他覺得現在的 VIP 資格吃人夠夠,希望用 || 邏輯運算子

Mary 說:「老闆我好歹是忠實老客戶欸,我買了你八年的薯條,而且遠遠超過 200 元,竟然還不算我是 VIP,你有沒有搞錯!」

老闆怕了,他很擔心會上台灣的老天鵝娛樂被當作笑柄,所以他立馬將 VIP 條件改成,只要符合以下任一點消費條件,就能成為 VIP 資格。

  1. 一次消費滿 200 元
  2. 一定要買 1 個漢堡

我們再看看 Mary 有沒有符合條件吧!

1
2
3
4
5
6
7
8
9
10
11
12
var VIPTotal = 200;
var hamburgerPrice = 50;
var friesPrice = 30;
var maryHamburgerNum = 0;
var maryfriesNum = 10;
var maryIsVIP;

// 如上面新增的變數,Mary買了0個漢堡,與10個薯條
// 請同時運用比較運算子與邏輯運算子,將比較結果寫在 markIsVIP 上
// maryIsVIP 的型別必須為布林值(true or false)

console.log("mary的 VIP 條件為"+ maryIsVIP)

第六天六角題目解答:

第一題

1
2
3
isVIP = (( 2 * hamburgerPrice ) + ( 2 * friesprice )) >= 200 ? 'true' : 'false';

console.log("Bob的 VIP 條件為"+isVIP) // false

第二題

1
2
3
4
5
6
7
markIsVIP = (( markHamburgerNum * hamburgerPrice ) + ( markfriesNum * friesprice )) >= 200 && markHamburgerNum >= 1 ? 'true' : 'false';

console.log("mark的 VIP 條件為"+ markIsVIP) // true

maryIsVIP = (( maryHamburgerNum * hamburgerPrice ) + ( maryfriesNum * friesprice )) >= 200 && markHamburgerNum >= 1 ? 'true' : 'false';

console.log("mary的 VIP 條件為"+ maryIsVIP) // false

第三題

1
2
3
maryIsVIP = (( maryHamburgerNum * hamburgerPrice ) + ( maryfriesNum * friesPrice )) >= VIPTotal || markHamburgerNum >= 1 ? 'true' : 'false';

console.log("mary的 VIP 條件為"+ maryIsVIP) // true

解題關鍵:善用三元運算子可以大幅縮減程式碼,只要記得公式就是 條件 ? 值1(如果前方條件成立) : 值2(如果前方條件不成立),當然也可以一直串接下去,比如 條件1 ? 值1(如果前方條件成立) : 條件2(當前方條件1不成立時觸發) ? 值2(如果前方條件2成立) : 值3(如果前方條件2不成立),用這種方式可以省去很多 if-else,但是在閱讀上可能要花點時間,所以要慎用!(因為本週講義有用到三元運算子,所以有刻意使用,其實後方的判斷都可以不用加上去)

Day7

第七天六角的題目為:

第一題 - if 的練習

老闆說現在要來驗收 if 成果,
成為 VIP 會員的條件,只要購買滿 200 元,
現在 會員 A 購買了 350 元,請用 if 判斷是否要給他 VIP 卡。

1
2
3
4
5
var VIPTotal = 200;
var memberPrice = 350;

// 請透過 if 來設計回覆,如果對方滿足門檻
// 就回覆 console.log("您好,您有達到 VIP 門檻。這裡給您 VIP 會員卡(遞上")

第二題 - if else 的練習

又有人來申請 VIP 活動了!
成為 VIP 會員的條件,只要購買滿 200 元,就可無條件成為會員,Mark 買了 2 個漢堡,2 個 薯條,是否有滿足條件?

這次要記得用 if,以及注意你的語氣啊~ (小杰覺得人生好難

1
2
3
4
5
6
7
var VIPTotal = 200;
var hamburgerPrice = 50;
var friesPrice = 30;

// 請透過 if else 來去設計對方是否有達到條件,有或沒有都需要回覆對方
// 如果有,請顯示 console.log("尊敬的客戶您好,您有達到 VIP 條件")
// 如果沒有達到條件,便用 else 顯示 console.log("尊敬的客戶您好,您還差 xx 元,才有符合 VIP 條件哦~")

第三題 - if、else if、else 練習

工作一整天,小杰累到懷疑人生,累歸累,但還是得吃東西,小杰吃東西有自己的 SOP,來幫幫小杰看看他該吃什麼食物。

  • 小杰都用飢餓度 1~100 來計算,100 就是代表最飢餓,數值皆為整數,不會有小數點
  • 小杰飢餓度 0~20 時,都吃飯糰
  • 小杰飢餓度在 21~40 時,都吃肉燥飯+貢丸湯
  • 小杰飢餓度在 41~60 時,都吃麥當勞
  • 小杰飢餓度在 61~100 時,都吃 99 元火鍋吃到飽
  • 今天小杰的飢餓度是 53,請引導小杰去指定地點用餐
1
2
3
4
5
6
7
8
9
10
var hungryNum = 53;

if(條件式){
console.log();
}else if{
console.log();
}

// 請用 if、else if 去判斷主人公該吃什麼
// 各區塊回覆內容請顯示 console.log("主人公因為飢餓度在"+hungryNum+",所以他決定去吃麥當勞")

第七天六角題目解答:

第一題

1
2
3
if(memberPrice >= VIPTotal) {
console.log("您好,您有達到 VIP 門檻。這裡給您 VIP 會員卡(遞上")
}

第二題

1
2
3
4
5
6
7
8
9
10
11
var MarkTotal = (2 * hamburgerPrice) + (2 * friesPrice); // 馬克實際購買金額
var shortage; // 放短少金額

if(MarkTotal >= VIPTotal) {
console.log("尊敬的客戶您好,您有達到 VIP 條件")
} else {
// 計算短少金額
shortage = VIPTotal - MarkTotal;

console.log("尊敬的客戶您好,您還差 " + shortage + " 元,才有符合 VIP 條件哦~")
}

第三題

1
2
3
4
5
6
7
8
9
if(hungryNum >= 0 && hungryNum <= 20) {
console.log("主人公因為飢餓度在"+hungryNum+",所以他決定去吃 飯糰")
} else if (hungryNum >= 21 && hungryNum <= 40) {
console.log("主人公因為飢餓度在"+hungryNum+",所以他決定去吃 肉燥飯+貢丸湯")
} else if (hungryNum >= 41 && hungryNum <= 60) {
console.log("主人公因為飢餓度在"+hungryNum+",所以他決定去吃 麥當勞")
} else if (hungryNum >= 61 && hungryNum <= 100) {
console.log("主人公因為飢餓度在"+hungryNum+",所以他決定去吃 99 元火鍋吃到飽")
}

解題關鍵:本日重點為 if、else、else if…,和昨日一樣,如果善用三元運算子其實可以省很多程式碼,但是有時候精確的寫出整行程式碼,也是算比較保險不容易出錯的方式哦!

Day8

第八天六角的題目為:

第一題 - 老闆考考你指派運算子

老闆:「我其實很懷疑你是不是真的會了,我考考你!」
老闆:「剛好今天是發薪日,先發給你薪資 23500 元(遞給小杰」
小杰:「謝謝腦闆,但你怎麼把我的薪資告訴大家了…」
老闆:「這不是重點,以下兩步驟動作請寫成程式」
老闆:「步驟一:因為你遲到一次,我要扣你 1000 元(取走小杰手上的 1000 元」
老闆:「步驟二:然後你又偷吃 Pizza,我要再扣你 2500 元 (再次取走」
小杰:「不是啊!那明明是小黑吃…」
老闆:「這不是重點,快點算!算出你還剩下多少錢!」

1
2
3
4
5
var salary = 23500;

// 請依照上面的武功秘笈Codepen,依序實現兩步驟,算出小杰被扣了多少錢

console.log("小杰目前還剩下"+salary+"元");

第二題 - if + 指派運算子

老闆:「好了,現在我要告訴你贈品條件!」

  • 目前小杰手上有 3 個贈品
  • 消費滿 100 元就送對方贈品

而現在來了兩個客人,並依序有消費,請問現在他還剩下多少個贈品?

1
2
3
4
5
6
7
8
var giftNum = 3; // 贈品數量
var customerA = 150;// 顧客 A 消費金額
var customerB = 99; // 顧客 B 消費金額

if(客戶A條件){}
if(客戶B條件){}

console.log("目前贈品剩下"+giftNum+"個");

第三題 - if+指派運算子

老闆:「我現在補齊給你總計 50 個贈品!」
老闆:「然後我覺得現在贈品門檻太高了,我決定大放送,只要滿 50 元就送一個!以此類推,他買 500 元就送 10 個贈品!」
小杰:「老闆你今天這麼慷慨,那我的薪…」
老闆:「別廢話,客人來了快點!他買完後告訴我贈品還夠不夠!」

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var giftNum = 50; // 贈品數量
var friesPrice = 30; // 薯條單價
var hamburgerPrice = 50; // 漢堡單價

// 以下是題目
// mary 買了 10 份薯條,10 份漢堡
// 請計算完贈品規則後,善用指派運算子去計算目前剩下的贈品有幾個
// 並用下面的 if 回報給老聞

if(){
console.log("老聞!贈品還夠!剩下"+giftNum+"個~" );
} else {
console.log("老聞贈品賣光啦~")
}

第八天六角題目解答:

第一題

1
2
3
salary = salary - 1000 - 2500;

console.log("小杰目前還剩下"+salary+"元"); // 20000

第二題

1
2
3
4
5
6
7
8
9
if(customerA > 100){
giftNum -= 1;
}
if(customerB > 100){
giftNum -= 1;
}

console.log("目前贈品剩下"+giftNum+"個"); // 2

第三題

1
2
3
4
5
6
7
8
var maryTotal = 10 * friesPrice + 10 * hamburgerPrice;

if(maryTotal > 50 && giftNum >= 0){
giftNum -= maryTotal / 50;
console.log("老聞!贈品還夠!剩下"+giftNum+"個~" ); // 34
} else {
console.log("老聞贈品賣光啦~")
}

解題關鍵:本日重點為運算子,A = A - B 可縮寫為 A -= B,和三元運算子一樣善用縮寫即可大幅縮寫程式碼。

Day9

第九天六角的題目為:

第一題 - 變數型別之呼吸

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
var a = 1;
a+=1;
a+=5;
var b = 5;
console.log(a+b);


var c = 3;
var d = "hello";
console.log(c*d);


var e = 8 + 2 * "9";
console.log(e);


var f = 1;
var g = "2";
var h = 3;
console.log(typeof(f+g+h));

第二題 - 運算子之呼吸

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var total = 200;
var isVip = true;
console.log(total>=200 && isVip);

var a = true;
var b = false;
console.log( a && b);
console.log( a || b);

var c = 10;
var d = 20;
var e = 30;
console.log(c==10 && d>=5 && e !== 20);
console.log(c==10 || d>=5 || e !== 20);
console.log(c==5 || d>=40 || e !== 30);

第三題 - 運算子之呼吸

請告知以下 console.log,哪些會印出?
如果你很閒,試試看最後一題改下布林值。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
var maryIsVIP = true;
if(maryIsVIP){
console.log("哇貴婦餒!");
}else{
console.log("你一定搞錯了,叫你們店長出來!");
}

var momSwim = false;
var girlfriendSwim = true;

if(momSwim && girlfriendSwim){
console.log("都不救,因為他們都會游泳");
}else{
console.log("小杰大喊:「你們誰不會游泳啊??」");
if(girlfriendSwim){
console.log("那你自己游上來!");
}else{
console.log("我先問我阿母會不會游泳!");
}

if(momSwim){
console.log("媽妳先自己游上來!");
}else{
console.log("媽我去救你!");
}
}

第九天六角題目解答:

第一題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
var a = 1;
a+=1; // 2
a+=5; // 7
var b = 5;
console.log(a+b); // 12


var c = 3;
var d = "hello";
console.log(c*d); // NaN


var e = 8 + 2 * "9";
console.log(e); // 26


var f = 1;
var g = "2";
var h = 3;
console.log(typeof(f+g+h)); // String

第二題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var total = 200;
var isVip = true;
console.log(total>=200 && isVip); // true

var a = true;
var b = false;
console.log( a && b); // false
console.log( a || b); // true

var c = 10;
var d = 20;
var e = 30;
console.log(c==10 && d>=5 && e !== 20); // true
console.log(c==10 || d>=5 || e !== 20); // true
console.log(c==5 || d>=40 || e !== 30); // false

第三題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
var maryIsVIP = true;
if(maryIsVIP){
console.log("哇貴婦餒!"); // 印出
}else{
console.log("你一定搞錯了,叫你們店長出來!"); // 當 maryIsVIP === flase 印出
}

var momSwim = false;
var girlfriendSwim = true;

if(momSwim && girlfriendSwim){
console.log("都不救,因為他們都會游泳"); // 當 momSwim === true 且 girlfriendSwim === true 印出
}else{
console.log("小杰大喊:「你們誰不會游泳啊??」"); // 印出
if(girlfriendSwim){
console.log("那你自己游上來!"); // 印出, 但可能會有生命危險
}else{
console.log("我先問我阿母會不會游泳!"); // 當 girlfriendSwim === false 印出
}

if(momSwim){
console.log("媽妳先自己游上來!"); // 當 momSwim === true 印出
}else{
console.log("媽我去救你!"); // 印出
}
}

解題關鍵:關於 truefalse 還有 運算子 的複習。

Day10

第十天六角的題目為:

第一題 - 客戶詢價函式,來更多個客人也不怕

請改設計一個詢價用的函式,並新增三個參數,依序為客戶姓名、薯條數量,漢堡數量。
同時來了三個客戶,請執行三次函式回報結果。

1
2
3
4
5
6
7
8
9
10
//定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var bobTotal;

// 請將Code寫在這,運算內容賦予到 bobTotal,
// 並要利用到 hamburgerPrice、friesPrice
// 算出 Bob 的提問。

console.log("Bob 您好,您詢問的金額總計為"+bobTotal+"元");

第二題 - 好多客戶都在問小杰,他們錢包剩下多少錢,小杰表示無言

下面截圖,請改設計一個查詢客戶錢包餘額用的函式,並新增四個參數,依序為客戶姓名、客戶錢包總額、薯條數量,漢堡數量。

同時來了三個客戶,請執行三次函式回報結果。

1
2
3
4
5
6
7
8
9
10
11
// 定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var markWallet = 200;
var markTotal;

// 請將Code寫在這,運算內容賦予到markTotal,
// 並要利用到 markWallet hamburgerPrice friesPrice
// 算出 mark購買後剩餘的金額。

console.log('馬克買完東西後,錢包剩下'+markTotal +'元')

第三題 - 好多人都擁有九折優惠券

這一題,換您來設計函式與參數看看。

突然間同時來了三個客戶,請執行三次函式回報結果。

1
2
3
4
5
6
7
8
9
10
11
12
// 定義薯條跟漢堡的金額(金額不可更改)
var hamburgerPrice = 50;
var friesPrice = 40;
var sale = 0.9;
var maryWallet = 5000
var maryTotal;

// 請將Code寫在這,運算內容賦予到 maryTotal,
// 並要利用到hamburgerPrice friesPrice sale maryWallet
// 算出 maryTotal 剩下的錢。

console.log( 'Mary買完東西後,錢包剩下'+ maryTotal +'元')

第十天六角題目解答:

第一題

1
2
3
4
5
function countTotal(customerName, hamburgerNum, friesNum) {
return `${customerName} 您好,您詢問的金額總計為 ${hamburgerNum * hamburgerPrice + friesNum * friesPrice} 元`;
}

console.log(countTotal(Bob, 10, 5)); // Bob 您好,您詢問的金額總計為 700 元

第二題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
var hamburgerPrice = 50;
var friesPrice = 40;
var markWallet = 200;
var markTotal; // 馬克花費

// 錢包工廠
function deposit(baseMoney) {
var base = baseMoney || 0; // 錢包金額
return {
// 計算花費
spendMoney: function(spendMoney) {
return base -= spendMoney;
},
// 返回錢包金額
countTotal: function() {
return base;
}
}
}

// 創建一個新的馬克錢包
var markDeposit = deposit(markWallet); // 馬克專屬的錢包

// 計算總花費
markTotal = 1 * hamburgerPrice + 2 * friesPrice; // 130
console.log(`馬克買完東西後,錢包剩下 ${markDeposit.spendMoney(markTotal)} 元`);

// 馬克再次花費
markTotal = 1 * hamburgerPrice; // 50
console.log(`馬克再次買完東西後,錢包剩下 ${markDeposit.spendMoney(markTotal)} 元`);

第三題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
var hamburgerPrice = 50;
var friesPrice = 40;
var sale = 0.9;
var maryWallet = 5000; // 瑪麗 錢包
var bobSpendTotal = 10000; // bob 錢包
var xiaojieWallet = 10; // 小杰 錢包

var maryTotal; // 瑪麗 花費
var bobTotal; // Bob 花費
var xiaojieTotal; // 小杰 花費

// 錢包工廠
function deposit(baseMoney) {
var base = baseMoney || 0; // 錢包金額
return {
// 計算花費
spendMoney: function(spendMoney) {
return base -= spendMoney;
},
// 返回錢包金額
countTotal: function() {
return base;
}
}
}

// 創建一個新的錢包
var maryDeposit = deposit(maryWallet); // 瑪麗 專屬的錢包
var bobDeposit = deposit(bobSpendTotal); // bob 專屬的錢包
var xiaojieDeposit = deposit(xiaojieWallet); // 小杰 專屬的錢包

// 計算 瑪麗 總花費
maryTotal = (1 * hamburgerPrice + 2 * friesPrice) * sale;
console.log(`瑪麗買完東西後,錢包剩下 ${maryDeposit.spendMoney(maryTotal)} 元`); // 4883

// 計算 bob 總花費
bobTotal = (5 * hamburgerPrice + 20 * friesPrice) * sale;
console.log(`bob買完東西後,錢包剩下 ${bobDeposit.spendMoney(bobTotal)} 元`); // 9055

// 計算 小杰 總花費
xiaojieTotal = 1 * hamburgerPrice * sale;
console.log(`小杰買完東西後,錢包剩下 ${xiaojieDeposit.spendMoney(xiaojieTotal)} 元`); // -35

解題關鍵:第十天因為要練習 Function,突然想到之前有練習過 閉包工廠 就剛好拿來練習了,好處是錢包可以一直往下扣,而且外面的變數如果都會用到往內移到 Function 內的話,跑完 Function 就會釋放記憶體,只會暫存錢包計算後的金額!本次為練習,關於 閉包工廠 還有許多可以改進的地方,還請各路大神手下留情。

Day11

第十一天六角的題目為:

第一題 - 老闆想要隨時扣你的薪水

老闆:「今天是發薪日,先發給你薪資 23500 元(遞給小杰」
老闆:「以下三步驟動作請寫成程式」
老闆:「步驟一:昨天你上廁所太久了,我要扣你 1000 元」
老闆:「步驟二:小黑說不喜歡你煮的狗食,我要再扣你 3500 元 (再次取走」
老闆:「步驟三:我今天心情不太好,扣個 500 元意思一下」
小杰:「屁啦!心情不太好關我啥事!」
老闆:「這不是重點,快點算!將之前的寫法換成函式,並增加一個參數,讓我方便何時扣你多少都沒問題」
老闆:「最後你寫的函式,要執行三次,每次都要回報你的總薪水剩下多少。」

1
2
3
4
5
var salary = 23500;

//請依照上面的武功秘笈Codepen,依序實現兩步驟,算出小杰被扣了多少錢

console.log("小杰目前還剩下"+salary+"元");

第二題 - if + 指派運算子

老闆:「好了,現在我要告訴你贈品條件!」

目前小杰手上有 3 個贈品
消費滿 100 元就送對方贈品
下為第八關程式碼,請依照以下邏輯進行改寫:

現在來了三個客人,並依序有消費,A顧客消費 150、B 顧客消費 99、C 顧客消費 110。
請設計一個函式,裡面代入一個參數為顧客消費金額,確認該客戶是否符合贈品條件,若符合就讓 giftNum 變數減少數量。
並依序執行三次函式,每次函式皆會 return 目前贈品數量剩下多少。

1
2
3
4
5
6
7
8
9
10
// 贈品數量 var giftNum = 3;

var customerA = 150; // 顧客 A 消費金額
var customerB = 99; // 顧客 B 消費金額
var customerC = 110; // 顧客 C 消費金額

if(客戶A條件){}
if(客戶B條件){}

console.log("目前贈品剩下"+giftNum+"個");

第三題 - if+指派運算子

老闆:「我現在補齊給你總計 200 個贈品!」
老闆:「然後我覺得現在贈品門檻太高了,我決定大放送,只要滿 50 元就送一個!以此類推,他買 500 元就送 10 個贈品!」
小杰:「老闆你竟然利用我的特休,我跟你沒完啦。」
老闆:「別廢話,客人來了快點!他買完後告訴我贈品還夠不夠!」

下為第八關程式碼,giftNum 已改為 200 份,請依照以下邏輯進行改寫:

請用函式改寫,同時來了三組客人,請用你寫的函式連續執行三次,來幫助顧客是否有符合贈品條件。
另外每次執行函式時,都必須告訴老闆一次目前贈品數量。
第一組客人:Mary 買了 10 份薯條,10 份漢堡
第二組客人:Bob 買了 1 份薯條
第三組客人:Tim 買了 20 份薯條,15 份漢堡

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var giftNum = 200;       // 贈品數量
var friesPrice = 30; // 薯條單價
var hamburgerPrice = 50; // 漢堡單價

// 以下是題目
// mary買了10份薯條,10份漢堡
// 請計算完贈品規則後,善用指派運算子去計算目前剩下的贈品有幾個
// 並用下面的 if 回報給老閱

if(){
console.log("老閱!贈品還夠!剩下"+giftNum+"個~");
} else {
console.log("老闖贈品賣光啦~")
}

第十一天六角題目解答:

第一題

1
2
3
4
5
6
7
8
9
10
11
12
var salary = 23500;

function payCutHandler(reduceMoney) {
console.log(`小杰目前還剩下${salary -= reduceMoney}元`);
}

// 昨天你上廁所太久了,我要扣你 1000 元
payCutHandler(1000);
// 小黑說不喜歡你煮的狗食,我要再扣你 3500 元
payCutHandler(3500);
// 我今天心情不太好,扣個 500 元意思一下
payCutHandler(500);

第二題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
var giftNum = 3;
var customerA = 150; // 顧客 A 消費金額
var customerB = 99; // 顧客 B 消費金額
var customerC = 110; // 顧客 C 消費金額

function sendGift(spendMoney) {
if(spendMoney >= 100 && giftNum > 0) {
console.log(`目前贈品剩下${giftNum -= 1}個`);
} else if (giftNum <= 0) {
console.log(`目前贈品不夠囉`);
} else {
console.log(`您的消費金額不夠!`);
}
}

sendGift(customerA); // 目前贈品剩下2個
sendGift(customerB); // 您的消費金額不夠!
sendGift(customerC); // 目前贈品剩下1個

第三題

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
var giftNum = 200;       // 贈品數量
var friesPrice = 30; // 薯條單價
var hamburgerPrice = 50; // 漢堡單價
var sendGiftDoorsill = 50; // 贈品門檻

// 以下是題目
// mary買了10份薯條,10份漢堡
// 請計算完贈品規則後,善用指派運算子去計算目前剩下的贈品有幾個
// 並用下面的 if 回報給老閱

function sendGift(friesNum, hamburgerNum) {
var spendTotal = friesPrice * friesNum + hamburgerPrice * hamburgerNum;
var sendGiftNum = Math.floor(spendTotal/sendGiftDoorsill);
giftNum -= sendGiftNum;
if(giftNum > 0) {
console.log(`老闆!贈品還夠!剩下${giftNum}個~`);
} else {
console.log(`老闆贈品賣光啦~`);
}
}

sendGift(10, 10); // 老闆!贈品還夠!剩下184個~
sendGift(1); // 老闆!贈品還夠!剩下184個~
sendGift(20, 15); // 老闆!贈品還夠!剩下157個~

解題關鍵:今天也是練習 Function 練習應用。

Day11-2

第十一天六角直播的額外題目為:

整理 OPENDATA 資料,並且篩選出自己要的陣列,另外筆者也補上了手動輸入後塞選的功能(前端老毛病),資料來源為 **台中政府資料開放平臺**,這次練習的題目為 iBike車站 且項目為下:

  1. 列出 iBike 的車站總數

    因為 CodePen 不能塞太多 JS 內容,所以資料內容有刪減過

  2. 列出 iBike 的所有車站名稱

  3. 列出關於 公園 相關的所有車站名稱

  4. 使用者輸入 input 後可以自動篩選(前端老毛病)

此次練習為整理 JSON 資料,並沒有 API 串接,所以 JSON 是直接複製過來的!

第十一天六角直播的額外題目解答:

解題關鍵:善用 array.forEach()include() 還有 innerHTML 等等功能,即可整理成自己想要的陣列,另外推薦一個觀念,盡量不要直接去改變最一開始拿到的資料,把自己需要的篩選出來後放到新的陣列,舊的就維持原本的樣子就好!

Day12

第十二天六角的題目為:

HTMLCSS 面板都壞掉了,你只能編輯 JS 面板,來去尋找線索

今天只有一題題目,有興趣的朋友可以試試哦!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<div class="key">
<!-- 區塊一 -->
<div class="keyItem keyItem1" >
<img src="https://hexschool.github.io/JSTraining/stage12/4.png" alt="">
</div>
<!-- 區塊二 -->
<div class="keyItem keyItem2">
<img src="https://hexschool.github.io/JSTraining/stage12/2.png" alt="">
</div>
<!-- 區塊三 -->
<div class="keyItem keyItem3">

</div>
<!-- 區塊四 -->
<div class="keyItem keyItem4" style="">

</div>
</div>
1
2
3
4
5
6
7
8
// 區塊一,路徑放錯了,得用 setAttribute 換 src 屬性,換成 1.png

// 區塊二,唯一有放對,不需更改


// 區塊三,請用 innerHTML,指定 keyItem3,讓他插入 3.png 圖片

// 區塊四,只能用 style 插入 background 4.png

第十二天六角題目解答:

1
2
3
4
5
6
7
8
9
10
// 區塊一,路徑放錯了,得用 setAttribute 換 src 屬性,換成 1.png
document.querySelector('.keyItem1 img').setAttribute('src', 'https://hexschool.github.io/JSTraining/stage12/1.png');

// 區塊二,唯一有放對,不需更改

// 區塊三,請用 innerHTML,指定 keyItem3,讓他插入 3.png 圖片
document.querySelector('.keyItem3').innerHTML = '<img src="https://hexschool.github.io/JSTraining/stage12/3.png" alt="3.png" />';

// 區塊四,只能用 style 插入 background 4.png
document.querySelector('.keyItem4').style.backgroundImage = "url('https://hexschool.github.io/JSTraining/stage12/4.png')";

解題關鍵:今天是針對 DOM 的練習操作!

Day13

第十三天六角的題目為:

幫助小杰修好體重機!

以下為 BMI 計算方式:

  1. BMI 計算為:體重(公斤) / 身高的平方(單位為公尺)
  • 例如 150 公分 50 kg = 50/(1.5*1.5) = 22.2 BMI 指數
  1. BMI 數值狀態如下
  • 體重過輕:BMI < 18.5
  • 正常:18.5≦BMI<24
  • 過重:24≦BMI<27
  • 輕度肥胖:27≦BMI<30
  • 中度肥胖:30≦BMI<35
  • 重度肥胖:BMI≧35

今天只有一題題目,有興趣的朋友可以試試哦!

1
2
3
4
5
6
7
8
9
10
function calculationBMI(height,kg){
var bmi = kg/(height/100*height/100)
if(bmi>20){
return "過胖!但能吃就是福,維持現況也沒什麼不好的~"
}else{
return "你很瘦~ㄕㄡˋ~~"
}
}

console.log(calculationBMI(178,70));

第十三天六角題目解答:

1
2
3
4
5
6
7
8
9
function calculationBMI(height,kg){
var bmi = kg / (height/100 * height/100);
return bmi >= 35 ? '重度肥胖' : bmi >= 30 ? '中度肥胖' : bmi >= 27 ? '輕度肥胖' : bmi >= 24 ? '過重' : bmi >= 18.5 ? '正常' : bmi > 0 ? '體重過輕' : '壞掉啦'
}

console.log(calculationBMI(178,70)); // 小杰 => 正常
console.log(calculationBMI(158,40)); // 小杰女友 => 體重過輕
console.log(calculationBMI(160,90)); // 小杰好友 => 重度肥胖
console.log(calculationBMI(0,0)); // 小杰的錢包 => 壞掉啦

解題關鍵:三元運算子 雖然有助於幫助縮短程式碼,但也要小心使用!

Day 14

第十四天六角的題目為:

再次幫助小杰修好體重機!

以下為 BMI 計算方式:

  1. BMI 計算為:體重(公斤) / 身高的平方(單位為公尺)
  • 例如 150 公分 50 kg = 50/(1.5*1.5) = 22.2 BMI 指數
  1. BMI 數值狀態如下
  • 體重過輕:BMI < 18.5
  • 正常:18.5≦BMI<24
  • 過重:24≦BMI<27
  • 輕度肥胖:27≦BMI<30
  • 中度肥胖:30≦BMI<35
  • 重度肥胖:BMI≧35

今天只有一題題目,有興趣的朋友可以試試哦!(這次要做輸入框可以輸入)

1
2
3
4
5
6
<input type="text" class="height input" id="js_height_input" placeholder="請輸入您的身高(公分)">
<input type="text" class="kg input" id="js_kg_input" placeholder="請輸入您的體重(公斤)">
<input type="button" class="send" value="計算" id="js_send_btn">
<p class="total">您的 BMI 指數為
<span class="BMI" id="js_bmi_span">-</span>
狀態是 <span class="status" id="js_status_span">-</span></p>

第十四天六角題目解答:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
// 監聽按鈕
document.querySelector('#js_send_btn').addEventListener('click', function(){
let height = parseInt(document.querySelector('#js_height_input').value);
let kg = parseInt(document.querySelector('#js_kg_input').value);

// 輸入框不是數字就 Return;
if(isNaN(height) === true || isNaN(kg) === true) {
// 替換文字
innerHandler();
return;
};
// Bmi 計算及結果
let bmi = kg / (height/100 * height/100);
let result = bmi >= 35 ? '重度肥胖' : bmi >= 30 ? '中度肥胖' : bmi >= 27 ? '輕度肥胖' : bmi >= 24 ? '過重' : bmi >= 18.5 ? '正常' : bmi > 0 ? '體重過輕' : '壞掉啦';
console.log(height, kg, bmi, result);
// 替換文字
innerHandler(bmi, result);
});

// 監聽輸入框
let inputEle = document.querySelectorAll("input");

inputEle.forEach(function(elem) {
elem.addEventListener("keyup", function() {
innerHandler();
});
});

// 替換文字
function innerHandler(bmi = '-', result = '-') {
console.log(bmi, result);
document.querySelector('#js_bmi_span').innerHTML = bmi;
document.querySelector('#js_status_span').innerHTML = result;
}

解題關鍵:練習監聽事件,另外要替多個物件加上監聽必須先使用 querySelectorAll 選好 DOM 後再跑 forEach 一個一個加上去。

Day15

第十五天六角的題目為:

改寫 Code,但這次 HTML 面板壞掉了,你唯一可以改的面板只有 CSS 與 JS 面板。

1
2
3
4
5
6
.blue{
color: blue;
}
.orange{
color: orange;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
var height = document.querySelector('.height');
var kg = document.querySelector('.kg');
var send = document.querySelector('.send');
var bmiDOM = document.querySelector('.BMI');
var statusDOM = document.querySelector('.status');
var BMIData = {
"overThin":{
class:"blue",
statusText:"體重過輕"
},
"normal":{
class:"orange",
statusText: "正常"
}
}
function calculationBMI(){
var thisHeight = parseInt(height.value);
var thisKg = parseInt(kg.value);
var bmi = thisKg / (thisHeight / 100 * thisHeight / 100)
if (bmi > 20) {
render("normal",bmi)
} else {
render("overThin",bmi);
}
}

function render(status,bmiText){
bmiDOM.textContent = bmiText;
statusDOM.textContent = BMIData[status].statusText;
statusDOM.classList.add(BMIData[status].class);
}

send.addEventListener("click",function(){
calculationBMI();
})

第十五天六角題目解答:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
.blue{
color: blue;
}
.green {
color: green;
}
.pink {
color: pink;
}
.orange{
color: orange;
}
.purple {
color: purple;
}
.red {
color: red;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
var height = document.querySelector('.height');
var kg = document.querySelector('.kg');
var send = document.querySelector('.send');
var bmiDOM = document.querySelector('.BMI');
var statusDOM = document.querySelector('.status');
var BMIData = {
'overThin':{
text:"體重過輕",
class:"blue",
},
'normal':{
text:"正常",
class:"green",
},
'overweight':{
text:"過重",
class:"pink",
},
'mildObesity':{
text:"輕度肥胖",
class:"orange",
},
'moderateObesity':{
text:"中度肥胖",
class:"purple",
},
'severeObesity':{
text:"重度肥胖",
class:"red",
},
'broken':{
text:"壞掉了",
class:"black",
}
}

// 監聽輸入框
var inputEle = document.querySelectorAll("input");

inputEle.forEach(function(elem) {
elem.addEventListener("keyup", function() {
// 替換文字及樣式
render();
});
});

// 計算體重
function calculationBMI(){
let thisHeight = parseInt(height.value);
let thisKg = parseInt(kg.value);

// 輸入框不是數字就 Return;
if(isNaN(thisHeight) === true || isNaN(thisKg) === true) {
// 警告並替換文字
alert('請輸入數字');
render();
return;
};

let bmi = thisKg / (thisHeight / 100 * thisHeight / 100);

if(bmi === Infinity) {
// 警告並替換文字
alert('請避免輸入結果為無窮大的數值');
render();
return;
}

bmi >= 35 ? render(bmi, 'severeObesity') : bmi >= 30 ? render(bmi, 'moderateObesity') : bmi >= 27 ? render(bmi, 'mildObesity') : bmi >= 24 ? render(bmi, 'overweight') : bmi >= 18.5 ? render(bmi, 'normal') : bmi > 0 ? render(bmi, 'overThin') : render(0, 'broken');

}

// 替換文字及樣式
function render(bmiText = '-', status = '-'){
bmiDOM.textContent = bmiText;
statusDOM.innerHTML = BMIData[status] !== undefined ? BMIData[status].text : '-';
BMIData[status] !== undefined ? statusDOM.classList = `status ${BMIData[status].class}` : statusDOM.classList = 'status';
}

send.addEventListener("click",function(){
calculationBMI();
})

解題關鍵:今天的練習重點為 關注點分離

Day16

第十六天六角的題目為:

練習 forEach 塞入字串至 HTML,之後將整合前幾天練習。

1
<ul class="list"></ul>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
var list = document.querySelector(".list")
var data = [];
data.push(
{
"name":"廖洧杰",
"height":178
}
)
data.push(
{
"name":"小乖",
"height":120
}
)
data.push(
{
"name":"小麗",
"height":140
}
)
data.push(
{
"name":"小新",
"height":80
}
)
data.push(
{
"name":"小華",
"height":50
}
)

data.forEach(function(item){
var str = "";
var content = '<li>'+item.name+"你的身高是"+item.height+'</li>'
str+=content;
list.innerHTML = str;
})

第十六天六角的解答為:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
var list = document.querySelector(".list")
var data = [];
data.push(
{
"name":"廖洧杰",
"height":178,
"kg": 70,
"bmi": 22,
"status": '正常'
}
)
data.push(
{
"name":"小乖",
"height":120,
"kg": 15,
"bmi": 10,
"status": '體重過輕'
}
)
data.push(
{
"name":"小麗",
"height":140,
"kg": 60,
"bmi": 31,
"status": '中度肥胖'
}
)
data.push(
{
"name":"小新",
"height":80,
"kg": 80,
"bmi": 125,
"status": '重度肥胖'
}
)
data.push(
{
"name":"小華",
"height":50,
"kg": 1,
"bmi": 4,
"status": '體重過輕'
}
)

var str = "";

data.forEach(function(item){
let content = `<li>${item.name}的身高為 ${item.height} 公分,體重是 ${item.kg} 公斤,BMI 數據為 ${item.bmi},狀態為${item.status}<li>`
str += content;
list.innerHTML = str;
});

解題關鍵:今天的練習重點為 forEach字串模板

Day16-2

第十六天六角直播的額外題目為:

使用 AXIOS 取得資料,並且整理近畫面,這次使用上次 Day11-2 的練習做更改,把資料來源改為使用 AXIOS 取得。

第十一天六角直播的額外題目解答:

現在打 API 使用 AXIOS 真的方便許多,但是最近在工作上使用必須去多做一層中介層,再打 API 的同時就必須要先檢查 Token,這時候就會知道自己對 AJAX 其實不熟練,這邊會再精進學習!

Day17

第十七天六角的題目為:

請查看下列程式碼後思考並回覆:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
var list = document.querySelector(".list")
var data = [];

data.push(
{
"name":"廖消杰",
"height":178
}
)
data.push(
{
"name":"小乖",
"height":120
}
)
data.push(
{
"name":"小麗",
"height":140
}
)
data.push(
{
"name":"小新",
"height":80
}
)
data.push(
{
"name":"小華",
"height":50
}
)


data.forEach(function(item){
var str = "";
var content = '<li>'+item.name+"你的身高是"+item.height+'</li>'
str += content;
list.innerHTML = str;
})
  1. str 放 forEach 外頭跟裡面的差異
  2. innerHTML 放 forEach 外頭跟裡面的差異
  3. innerHTML 當要寫內容進去時,會不會將裡面內容給覆蓋掉?

第十七天六角的題目解答為:

  1. 如果放外頭不會每次都清掉,因為我們的目的是為了把字串暫時放在 str 這個變數,然後印到 HTML 上,如果放外面,會一直累加上去,這不是我們要的。
  2. forEach 會去跑一個 Array 迴圈,如果把 innerHTML 放外面只會跑一次,放回圈內才會在遍歷迴圈時每次都跑到。
  3. 會!如果不想要覆蓋就要使用 append

Day18

第十八天六角的題目為:

挑戰者們不要忘了,JS 始終要搭配妳寫好的 CSS 來進行渲染,護理師好像已經看膩了小杰爛到不行的陽春版本,寫了一個 .list2 版本,請依照他的 CSS 樣式邏輯,將 data 陣列裡面的資料,依序渲染到 .list2 裡面的 li 來顯示。

1
2
3
4
5
6
7
8
9
10
11
12
<ul class="list"></ul>

<ul class="list2">
<li class="list-card">
<h2>小華</h2>
<p>你的身高是178</p>
</li>
<li class="list-card">
<h2>小美</h2>
<p>你的身高是133</p>
</li>
</ul>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
.list2{
list-style:none;
margin: 0;
padding: 0;
}

.list-card{
background: blue;
width: 300px;
margin: 0 auto;
color: #fff;
text-align: center;
padding: 10px;
margin-bottom: 30px;
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
var list = document.querySelector(".list")
var data = [];
data.push(
{
"name":"廖洧杰",
"height":178
}
)
data.push(
{
"name":"小乖",
"height":120
}
)
data.push(
{
"name":"小麗",
"height":140
}
)
data.push(
{
"name":"小新",
"height":80
}
)
data.push(
{
"name":"小華",
"height":50
}
)
var str = "";
data.forEach(function(item){

var content = '<li>'+item.name+"你的身高是"+item.height+'</li>'
str+=content;

})
list.innerHTML = str;

第十八天六角的題目解答為:

解題關鍵:今天的練習重點為 字串模板 及變數應該放 function 外面還是裡面,這必須考量到你的變數是要每次在使用前都要回覆最初樣貌,還是要拿來累加上去。

Day19

第十九天六角的題目為:

參考同學的程式碼並解釋下列三個問題。

  1. arrayBMIrecord 的陣列用途是什麼?
  2. 請描述 calculateBMI 函式做了什麼事情
  3. 請描述 render 函式做了什麼事情

第十九天六角的題目解答為:

  1. arrayBMIrecord 的陣列用途是什麼?
    A: 用來放計算使用者輸入資料後使用者的身高體重BMI等等
  2. 請描述 calculateBMI 函式做了什麼事情
    A: 定義一個新的物件 userRecord 紀錄使用者的資料並把計算後的 BMI 放入,最後放到 arrayBMIrecord 陣列後並渲染到畫面上
  3. 請描述 render 函式做了什麼事情
    A: 將陣列內的資料組成 HTML 字串並渲染到畫面上

解題關鍵:今日為複習。

Day20

第二十天六角的題目為:

試著練習把之前的 計算樣式字串模板插入…等等 整合練習。

第二十天六角的題目解答為:

解題關鍵:今天算是總複習。

Day21

第二十一天六角的題目為:

將所有紀錄的 BMI 計算出平均值並且 Render 到畫面上。

第二十一天六角的題目解答為:

解題關鍵:今日練習了平均值的計算 Array.prototype.reduce(),這個用法會將陣列所有數字將起來,詳情可見 MDN

Day22

第二十二天六角的題目為:

紀錄渲染到畫面上為上到下,因為原本的題目是把紀錄存到一個變數陣列裡,然後透過 innerHTML 渲染到畫面上,但因為自己做法不同,所以這邊其實只動了一個地方。

第二十二天六角的題目解答為:

原本的做法需要先把陣列透過 reverse() 或是 unshift() 去反轉陣列,然後在渲染到畫面上。因為我原本的做法是直接把文字渲染到畫面上,並無需再透過陣列去存放,所以只改了 record_dom.insertAdjacentHTML('beforeend', html); 這段,把 beforeend 改為 afterbegin 前為 在 element 裡面,最後一個子元素之後 後者為 在 element 裡面,第一個子元素之前

解題關鍵:關於原本的 reverse()unshift(),雖然都是反轉,但其實在大資料處理上效能相差甚多,在網路上不乏可見許多人相比的文章,比如 Array的push與unshift方法效能比較分析Script。大概的概念就是,前者是 元素放進去後再一次反轉,後者為 元素放進第一個後,每一個元素一個一個往後移動,在大多數的比較下,兩者的秒數相差都有十幾倍以上,所以這邊選擇使用 push() 後再 reverse()

Day23

第二十三天六角的題目為:

須將變數 title 的值塞入陣列 monthMoney 第一個位置。

1
2
var monthMoney = [ 500000, 1300000,2000000];
var title = '總公司每月討債業績';

第二十三天六角的題目解答為:

解題關鍵:因為本次不需要反轉陣列,所以不需要用到 reverse(),只需要使用 unshiift(),這個用法類似於 push(),只是是將數值塞入順序第一位。

Day24

第二十四天六角的題目為:

使用 forEach()newMonthMoney 陣列的值依序放到 monthMoney 的後方。

第二十四天六角的題目解答為:

解題關鍵:使用 forEach() 可以依序對陣列內的值進行操作!

Day25

第二十五天六角的題目為:

將陣列 serverData 內的物件重新排列,需要改為 data = [["總公司每月討債業務",500000, 1300000,2000000,300000,500000],["黑道大哥業績",30000,100000,300000,50000,100000]]

1
2
3
4
5
6
7
8
9
10
11
12
13
var serverData = [
{
"name":"總公司每月討債業務",
"seasonOneData":[500000, 1300000],
"seasonTwoData":[2000000,300000,500000]

},{
"name":"黑道大哥業績",
"seasonOneData":[30000,100000],
"seasonTwoData":[300000,50000,100000]
}
]
var data=[];

第二十五天六角的題目解答為:

解題關鍵:又到了快樂星期五,今天用了一直很想嘗試的解構,看來要再多練習呢!

Day26

第二十六天六角的題目為:

練習 AJAX 取得資料並渲染到畫面上。

第二十六天六角的題目解答為:

解題關鍵:之後題目又會回到 AJAX 了,今日為複習。

Day27

第二十七天六角的題目為:

參考下列三個網站學習不熟或沒用過的寫法。

第二十七天六角的題目解答為:

這邊自己挑了兩個沒用過的用法來學習,分別是 copyWithin()Array.from(),前者可將陣列內指定的位置替換掉,並且複製內列內指定的區間值覆蓋上去,舉例來說有個陣列為 [1, 2, 3, 4, 5] 用前者方法可以將陣列內容的 4, 5 替換為 1, 2;後者為 Array.forEach()Object 版本。

解題關鍵:在資料處理中就是 JavaScript 的精華了,如果能更熟悉一些用法,可以避免掉很多多餘的程式碼。

Day28

第二十八天六角的題目為:

取得 API 後在使用 sort() 去排序。

第二十八天六角的題目解答為:

解題關鍵:取得資料後使用 sort() 排序可從小排到大或是從大排到小。

Day29

第二十九天六角的題目為:

繼昨天的串接 API 之後排序,今日需要加上 Select 並且按造使用者選擇的選項去排序,HTML 範例為:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<select>
<option value="id">依照 id 編號排序(由1開始從上往下)</option>
<option value="process">依照完課率排序(由最高到最低)</option>
</select>

// 以下為編號排序範例
<ul class="list">
<li>編號 ID 1 為廖洧杰,他的完成進度為 5 %</li>
<li>編號 ID 2 為王小明,他的完成進度為 33 %</li>
</ul>

// 以下為完課率排序範例
<ul class="list">
<li>編號 ID 2 為王小明,他的完成進度為 33 %</li>
<li>編號 ID 1 為廖洧杰,他的完成進度為 5 %</li>
</ul>

第二十九天六角的題目解答為:

解題關鍵:使用監聽事件 DOM.addEventListener() 後傳值進 render()function,這邊傳送 Select 底下 OptionValue,這樣可以直接在 render 的時候直接去對到列內的 key,所以之後有新增想排序的選項,可以在 option 那邊先把 value 定義好。

Day30

第三十天六角的題目為:

依照昨天的 API 取的列表後,經過 sort() 之後的陣列必需轉為圖表。

第三十天六角的題目解答為:

這次會用到 **c3.js**,這是一個開源的圖表套件,代表可以免費使用且方便上手,只是用別人的套件最大的問題就是格式必須按照對方的排法,因為之前是用 d3.js 但也僅止於用 excel 的地方。

在開始我們必須引入 CSSJS

1
2
<link href="https://cdnjs.cloudflare.com/ajax/libs/c3/0.7.18/c3.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/c3/0.7.18/c3.min.js"></script>

完成後的起手勢跟 canvas 很像,必須先在 html 上選擇你要放表的地方:

1
<div id="chart"></div>

接著按照最基本的 c3 line 教學,初始化圖表:

1
2
3
4
5
6
7
8
var chart = c3.generate({
data: {
columns: [
['data1', 30, 200, 100, 400, 150, 250],
['data2', 50, 20, 10, 40, 15, 25]
]
}
});

接著就能看見圖表了,但你可能還會想配置一些額外的設定,比方說 X 及 Y 軸的文字顏色圖表樣式…等等。

Axis(軸)

關於配製方法幾乎都是在 c3.generate 裡面 data 的下方一個一個補上去,像是現在要舉例的 Axis(軸) 就向下方的寫法:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
var chart = c3.generate({
data: {
columns: [
['data1', 30, 200, 100, 400, 150, 250, 50, 100, 250]
// 可配置多個
]
},
axis: {
x: {
type: 'category',
categories: ['小杰', '老闆', '黑道大哥', '護理師', '禿頭俠', '路人甲', '路人乙', '路人丙', '你'],
label: {
text: '參賽者姓名',
position: "outer-center"
// inner-right : default
// inner-center
// inner-left
// outer-right
// outer-center
// outer-left
},
},
y: {
label: {
text: '完課率(%)',
position: 'outer-middle'
// inner-top : default
// inner-middle
// inner-bottom
// outer-top
// outer-middle
// outer-bottom
}
},
}
});

相關配置其實都還是可以在官方指南找到,這邊就淺入淺出吧!

解題關鍵:其實套件使用還是要看當初作者怎麼訂製,然後使用,主要需要注意的地方還是在資料處理部分,該怎麼塞,怎麼重複使用同一個 function 不寫多餘的 Code,這才是最重要的地方,有關圖表更多介紹可以參考這位大神的部落格 提姆寫程式(TimCodingBlog) - JS 筆記 - C3.js 基本認識


Conclusion & 結論

目前會每天依序的練習,如果有解開題目答案或是不了解也可以在下方留言呦!如果題目出得不好也請各路大神手下留情。