การตรวจสอบประเภท

*เนื้อหานี้แปลโดยใช้ AI (เวอร์ชัน Beta) และอาจมีข้อผิดพลาด หากต้องการดูหน้านี้เป็นภาษาอังกฤษ ให้คลิกที่นี่

Luau รองรับระบบประเภทอย่างค่อยเป็นค่อยไปผ่านการใช้การระบุประเภทและการอนุมาน ประเภทเหล่านี้ใช้เพื่อให้คำเตือน ข้อผิดพลาด และคำแนะนำที่ดีกว่าใน Script Editor

กำหนดประเภท

ใช้ type คำหลักเพื่อกำหนดประเภทของคุณเอง:


type Vector2 = {x: number, y: number}

โหมดการอนุมาน

มีโหมดการอนุมานประเภท Luau สามโหมดที่สามารถตั้งค่าได้ในบรรทัดแรกของ Script:

  • --!nocheck — ไม่ตรวจสอบประเภท
  • --!nonstrict — กำหนดประเภทตัวแปรเฉพาะเมื่อมีการระบุไว้อย่างชัดเจน
  • --!strict — กำหนดประเภททั้งหมดตามประเภทที่อนุมานหรือระบุไว้อย่างชัดเจน

โหมด --!nonstrict และ --!strict ควบคุมว่าตัวตรวจสอบประเภทเข้มงวดเพียงใดในการอนุมานและตรวจสอบประเภทสำหรับตัวแปรและฟังก์ชัน การไม่ตรงกันของประเภทในสคริปต์จะเน้นใน Script Editor และแสดงเป็นคำเตือนในหน้าต่าง Script Analysis

ในการตั้งค่าโหมดเริ่มต้นสำหรับสคริปต์ทั้งหมดที่คุณสามารถเปลี่ยนแปลงตามต้องการ ให้ดูที่ Workspace.LuauTypeCheckMode

ประเภท

การระบุประเภทสามารถทำได้โดยใช้ : ตัวดำเนินการหลังจากตัวแปรท้องถิ่นจากนั้นตามด้วยการกำหนดประเภท โดยค่าเริ่มต้น ในโหมด nonstrict ตัวแปรทั้งหมดจะถูกกำหนดประเภทเป็น any


local foo: string = "bar"
local x: number = 5

มีสี่ประเภทพื้นฐานที่สามารถใช้ในคำระบุประเภท:

  • nil - ไม่มีค่า
  • boolean - true หรือ false
  • number - ค่าตัวเลข
  • string - ข้อความ

ภายใน Roblox ทุกคลาส ประเภทข้อมูล และ enum จะมีประเภทของตนเองที่คุณสามารถตรวจสอบได้:


local somePart: Part = Instance.new("Part")
local brickColor: BrickColor = somePart.BrickColor
local material: Enum.Material = somePart.Material

หากต้องการทำให้ประเภทเป็นทางเลือก ให้ใช้ ? ที่ปลายของการระบุ:


local foo: string? = nil

สิ่งนี้จะทำให้ตัวแปรสามารถเป็นประเภทที่ระบุ (ในกรณีนี้คือ string) หรือ nil

ประเภทลิทเทอรัล

คุณยังสามารถแคสต์สตริงและบูลีนเป็นค่าลิทเทอรัลแทนที่จะใช้ string และ boolean:


local alwaysHelloWorld: "Hello world!" = "Hello world!"
alwaysHelloWorld = "Just hello!" -- ข้อผิดพลาดประเภท: ประเภท '"Just hello!"' ไม่สามารถแปลงเป็น '"Hello world!"' ได้
local alwaysTrue: true = false -- ข้อผิดพลาดประเภท: ประเภท 'false' ไม่สามารถแปลงเป็น 'true' ได้

การแคสต์ประเภท

บางครั้งคุณอาจต้องช่วยตัวตรวจสอบประเภทด้วยการแคสต์ค่าหนึ่งไปยังประเภทที่แตกต่างด้วย :: ตัวดำเนินการ:


local myNumber = 1
local myString: string
myString = myNumber -- ไม่ใช่ OK; ข้อผิดพลาดการแปลงประเภท
myString = myNumber :: any -- OK; การแสดงออกทั้งหมดสามารถแคสต์เป็น 'any'
local myFlag = myNumber :: boolean -- ไม่ใช่ OK; ประเภทไม่เกี่ยวข้อง

การกำหนดประเภทฟังก์ชัน

พิจารณาฟังก์ชันต่อไปนี้:


local function add(x, y)
return x + y
end

ฟังก์ชันนี้ทำการบวก x เข้ากับ y แต่จะเกิดข้อผิดพลาดหากหนึ่งหรือทั้งสองเป็นสตริง Luau ไม่รู้ว่าฟังก์ชันนี้สามารถใช้เฉพาะตัวเลขเท่านั้น เพื่อป้องกันปัญหาประเภทนี้ ให้เพิ่มประเภทไปยังพารามิเตอร์:


local function add(x: number, y: number)
return x + y
end

Luau ตอนนี้รู้ว่าฟังก์ชันรับสองตัวเลขและโยนคำเตือนหากคุณพยายามส่งมอบสิ่งใดที่ไม่ใช่ตัวเลขไปยังฟังก์ชัน:


add(5, 10)
add(5, "foo") -- ข้อผิดพลาดประเภท: สตริงไม่สามารถแปลงเป็นตัวเลขได้

ในการกำหนดประเภทการคืนค่า ให้ใส่ตัวดำเนินการ : ที่ปลายการนิยามฟังก์ชัน:


local function add(x: number, y: number): number

หากต้องการคืนค่าหลายประเภท ให้วางประเภทในวงเล็บ:


local function FindSource(script: BaseScript, pattern: string): (string, number)
return 42, true -- ข้อผิดพลาดประเภท
end

กำหนดประเภทฟังก์ชัน

ประเภทฟังก์ชันสามารถกำหนดโดยใช้ไวยากรณ์ (in) -> out โดยใช้ฟังก์ชันจากตัวอย่างก่อนหน้า ประเภทของฟังก์ชันมีดังนี้:


type add = (x: number, y: number) -> number
type FindSource = (script: BaseScript, pattern: string) -> (string, number)

ประเภทตาราง

Luau ไม่มีประเภท table; แทนที่จะเป็นประเภทตารางจะถูกกำหนดโดยใช้ไวยากรณ์ {} หนึ่งวิธีในการกำหนดตารางคือการใช้ไวยากรณ์ {type} ซึ่งกำหนดประเภทรายการ


local numbers: {number} = {1, 2, 3, 4, 5}
local characterParts: {Instance} = LocalPlayer.Character:GetChildren()

กำหนดประเภทดัชนีโดยใช้ {[indexType]: valueType}:


local numberList: {[string]: number} = {
Foo = 1,
Baz = 10
}
numberList["bar"] = true -- ข้อผิดพลาดประเภท: บูลีนไม่สามารถแปลงเป็นตัวเลขได้

ตารางยังสามารถมีดัชนีสตริงที่ชัดเจนกำหนดในประเภทได้


type Car = {
Speed: number,
Drive: (Car) -> ()
}
local function drive(car)
-- ไปตามขีดจำกัดความเร็วเสมอ
end
local taxi: Car = {Speed = 30, Drive = drive}

Variadics

นี่คือฟังก์ชันที่คำนวณผลรวมของจำนวนใด ๆ :


local function addLotsOfNumbers(...)
local sum = 0
for _, v in {...} do
sum += v
end
return sum
end

ตามที่คาดไว้ ฟังก์ชันนี้สามารถรับค่าใด ๆ และตัวตรวจสอบประเภทจะไม่เกิดคำเตือนหากคุณจัด提供ประเภทที่ไม่ถูกต้อง เช่น string


print(addLotsOfNumbers(1, 2, 3, 4, 5)) -- 15
print(addLotsOfNumbers(1, 2, "car", 4, 5)) -- พยายามบวกสตริงเข้ากับตัวเลข

แทนที่จะเป็นเช่นนั้นให้กำหนดประเภทให้กับ ... เช่นเดียวกับวิธีที่คุณกำหนดประเภทอื่น ๆ :


local function addLotsOfNumbers(...: number)

และตอนนี้บรรทัดที่สองจะก่อให้เกิดข้อผิดพลาดประเภท


print(addLotsOfNumbers(1, 2, 3, 4, 5))
print(addLotsOfNumbers(1, 2, "car", 4, 5)) -- ข้อผิดพลาดประเภท: สตริงไม่สามารถแปลงเป็นตัวเลขได้

อย่างไรก็ตาม สิ่งนี้ไม่ทำงานเมื่อคุณเขียนการนิยามประเภทฟังก์ชัน:


type addLotsOfNumbers = (...: number) -> number -- คาดประเภท แต่ได้ ':'

แทนที่จะเป็นเช่นนั้นให้ใช้ไวยากรณ์ ...type เพื่อกำหนดประเภทที่เปลี่ยนแปลงได้


type addLotsOfNumbers = (...number) -> number

ยูเนียนและการตัดกัน

คุณสามารถกำหนดประเภทเป็นสองหรือหลายประเภทโดยใช้การรวมกลุ่มหรือการตัดกันได้:


type numberOrString = number | string
type type1 = {foo: string}
type type2 = {bar: number}
type type1and2 = type1 & type2 -- {foo: string} & {bar: number}
local numString1: numberOrString = true -- ข้อผิดพลาดประเภท
local numString2: type1and2 = {foo = "hello", bar = 1}

กำหนดประเภทที่อนุมาน

คุณสามารถใช้ฟังก์ชัน typeof ในการกำหนดประเภทสำหรับประเภทที่อนุมาน:


type Car = typeof({
Speed = 0,
Wheels = 4
}) --> Car: {Speed: number, Wheels: number}

แนวทางหนึ่งในการใช้ typeof คือการกำหนดประเภทของเมตาตารางโดยใช้ setmetatable ภายในฟังก์ชัน typeof:


type Vector = typeof(setmetatable({}::{
x: number,
y: number
}, {}::{
__add: (Vector, Vector|number) -> Vector
}))
-- Vector + Vector จะคืนค่าประเภท Vector

เจเนอริก

เจเนอริกเป็นพารามิเตอร์สำหรับประเภทในระดับพื้นฐาน พิจารณาออบเจกต์ State ต่อไปนี้:


local State = {
Key = "TimesClicked",
Value = 0
}

หากไม่มีเจเนอริก ประเภทสำหรับออบเจกต์นี้จะเป็นดังนี้:


type State = {
Key: string,
Value: number
}

อย่างไรก็ตาม คุณอาจต้องการให้ประเภทสำหรับ Value ขึ้นอยู่กับค่าที่เข้ามา ซึ่งเป็นจุดที่เจเนอริกเข้ามา:


type GenericType<T> = T

<T> หมายถึงประเภทที่สามารถตั้งค่าเป็นสิ่งใดก็ได้ วิธีที่ดีที่สุดในการมองเห็นสิ่งนี้คือการแทนที่ประเภท


type List<T> = {T}
local Names: List<string> = {"Bob", "Dan", "Mary"} -- ประเภทกลายเป็น {string}
local Fibonacci: List<number> = {1, 1, 2, 3, 5, 8, 13} -- ประเภทกลายเป็น {number}

เจเนอริกยังสามารถมีการแทนที่หลายๆ บัญชีภายในวงเล็บ


type Map<K, V> = {[K]: V}

เพื่อปรับปรุงออบเจกต์ State จากก่อนหน้านี้เพื่อใช้ประเภทเจเนอริก:


type State<T> = {
Key: string,
Value: T
}

ฟังก์ชันเจเนอริก

ฟังก์ชันยังสามารถใช้เจเนอริก ในตัวอย่าง State ค่าของ T จะถูกอนุมานจากอาร์กิวเมนต์ที่เข้ามาของฟังก์ชัน

ในการกำหนดฟังก์ชันเจเนอริกให้เพิ่ม <> ไปยังชื่อฟังก์ชัน:


local function State<T>(key: string, value: T): State<T>
return {
Key = key,
Value = value
}
end
local Activated = State("Activated", false) -- State<boolean>
local TimesClicked = State("TimesClicked", 0) -- State<number>

การส่งออกประเภท

เพื่อให้ประเภทสามารถใช้งานได้ภายนอก ModuleScript ให้ใช้คำหลัก export:

โมดูลประเภทใน ReplicatedStorage

export type Cat = {
Name: string,
Meow: (Cat) -> ()
}
สคริปต์ที่ใช้โมดูลประเภท

local ReplicatedStorage = game:GetService("ReplicatedStorage")
local Types = require(ReplicatedStorage.Types)
local newCat: Types.Cat = {
Name = "metatablecat",
Meow = function(self)
print(`{self.Name} said meow`)
end
}
newCat:Meow()
©2026 Roblox Corporation. Roblox, โลโก้ Roblox และ Powering Imagination เป็นส่วนหนึ่งของเครื่องหมายการค้าที่จดทะเบียน และไม่ได้จดทะเบียนของเราในสหรัฐฯ และประเทศอื่นๆ