iT邦幫忙

0

【TypeScript】TypeHero - TS 初心者的練習

  • 分享至 

  • xImage
  •  

https://ithelp.ithome.com.tw/upload/images/20240126/20149362UagmaueXZA.jpg

大家好,最近開始在學 TypeScript,除了官方文件以外,也偶爾會翻閱保哥的免費電子書 will 保哥 - TypeScript 新手指南TS 影片介紹
TypeHero 這個網站也是個很棒的學習資源~ 如果想把 TypeScript 學扎實的人,千萬不要錯過它!!

Summary

這篇文章主要會圍繞在 TypeHero 和記錄我自己刷題的心得
會挑選兩題適合新手的題目(新手是我 (〃∀〃)

  • TypeHero 是什麼
  • 題目一:Primitive Data Types
  • 題目二:Type Aliases

TypeHero 是什麼

TypeHero 是由一位 Netflix 的資深工程師所開發的開源專案。可以把它想成是 TypeScript 版的 Leecode,上面從簡單到困難的 TypeScript 題目都有!例如以 TypeHero 的「TypeScript Foundations」12 道題目來說,它涵蓋了從基礎語法到進階概念的一系列題目,幫助我們消化、應用各個知識點。像是「原始資料型別」、「型別別名」、「字串字面量型別」、「索引簽名」、「typeof」等。此外只要有 Github 帳號,登入後即可開始刷題!

以下擷取自 六角學院 - TS每日任務

  • 適合新手: Tracks > TypeScript Foundations 的 12 道基礎題目
  • 適合泛型新手:Explore > Beginner 想多練習更多初階泛型應用可以試試看 Beginner 裡的 14 道初階泛型題目
  • 適合寫過 1 年經驗的 TypeScript 開發者:Explore > Easy
  • 適合中階開發者:Explore > Medium

TypeHero 網址 https://typehero.dev/
GitHub 開源專案 https://github.com/typehero/typehero


題目一:Primitive Data Types

第一題就以「原始型別」作為開門見山,因為 TypeScript 的基礎概念之一就是能夠創建原始類型
題目簡述:需要在代碼中添加原始類型,直到錯誤消失為止。解題中你可能會需要為物件添加上消失的屬性

題目

const playSong = (artistName, year) => {
  return `${artistName} was released in the year ${year}`;
};

const artistName = 'Frank Zappa';

const age = 52;

interface Musician {
  artistName: string;

  // add the rest
}

const musicianInfo = ({ artistName, age, deceased }) => {
  return `${artistName}, age ${age}${deceased ? ' (deceased)' : ''}`;
};

musicianInfo({
  artistName,
  age,
  deceased: true,
});

答案

// playSong 函式帶入了兩個參數 artistName 以及 year,從以下的變數宣告可以知道型別分別是 string 和 number
const playSong = (artistName: string, year: number) => {
	return `${artistName} was released in the year ${year}`;
};

// 這兩個變數在 TypeHero 編輯器裡沒有出現紅色蚯蚓警告有錯,所以一開始忘記定義,送出就報錯了
const artistName: string = "Frank Zappa"; 
const age: number = 52;

// 介面的名稱:開頭要大小寫,代表一個型別
interface Musician {
	artistName: string;
	age: number;
	// 這裡官方有提示,下面也可以看到其實 musicianInfo 函式會帶入三個參數,唯獨少了 deceased
    // 在 interface 中物件必須跟介面的定義一致,多出或少了介面中的屬性都不行
	deceased: boolean;
}

// musicianInfo 接受一個物件作為參數,這個參數必須符合 Musician 的介面結構
const musicianInfo = ({ artistName, age, deceased }: Musician) => {
	return `${artistName}, age ${age}${deceased ? " (deceased)" : ""}`;
};

musicianInfo({
	artistName,
	age,
	deceased: true,
});

補充
物件型別(Object type)
- 物件
- function
- array
- Date
- RegExp
- Error

小總結

針對這道題目和這段代碼做個簡單的總結

const musicianInfo = ({ artistName, age, deceased }: Musician) => {...}
  • 結構賦值:在 musicianInfo 函式的參數中,{ artistName, age, deceased } 進行了結構賦值。當一個符合 Musician 介面結構的物件被傳遞給 musicianInfo 函式時,這個物件的 artistName、age 和 deceased 屬性會被提取出來
  • 型別註釋:Musician 這部分是對參數的型別註釋。它告訴 TypeScript 編譯器傳給 musicianInfo 函式的物件必須符合 Musician 介面的結構
  • 在 TypeScript 中,原始型別會以小寫字母定義
  • 除了原始型別外,TypeScript 還有一些較為進階的類型,如 symbol、bigint、object、never、unknown 和 any

題目二:Type Aliases

題目二是要使用型別別名(type aliases)來去定義型別
題目簡述:創建必要的型別別名,如 Name、Year、Payload(甚至是別的),請仔細閱讀測試

題目

// We completed the first alias (`Name`) for you to see as an example
type Name = string;

// Now try replacing `unknown` with a primitive data type that might be appropriate for `Year`
type Year = unknown;

type IsOperational = unknown;

type Payload = {
  name: Name;

  // the tests show that you need a `mass` property here
  // but first you might need to create an alias for `Kilograms`
  // because that's the value of `mass`
};

答案

// We completed the first alias (`Name`) for you to see as an example
type Name = string;

type Year = number; // 型別從底下測試可得知
type Count = number; // 從底下測試的 Spacecraft 介面 裡會知道 Count 用於計數,所以型別應是數字
type IsOperational = boolean; // 型別從底下測試可得知

// create an alias for `Kilograms`
type Kilograms = number; 

type Payload = {
  name: Name;
  mass: Kilograms;
  // the tests show that you need a `mass` property here
  // but first you might need to create an alias for `Kilograms`
  // because that's the value of `mass`
};

這題需仔細閱讀下方的測試code,因為大部分的型別都可以從底下測試得知,包含 Payload 裡有 mass 屬性也是

小總結

  • 建立型別別名就是使用「type」這個關鍵字
  • type 後發定義的命名並沒有強制規定一定要大寫開頭,但一般還是以大寫開頭,以提高code的可讀性和易讀性
  • 型別別名允許為任何型別定義一個新名稱。不僅僅是簡單的重新命名,還可以建立更複雜的型別結構,尤其是複雜的物件或聯合型別
  • 不要過度使用,像是可以直接使用 Row[],就不應該創建 Rows 這樣的別名

如果文章內有任何錯誤或是描述不清的地方,歡迎留言讓我知道 /images/emoticon/emoticon41.gif

參考來源

TypeHero 大挑戰
TypeHero


圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言