ทำไมคุณต้องระบุชนิดข้อมูลเมื่อประกาศตัวแปร?


41

ในภาษาการเข้ารหัสส่วนใหญ่ (ถ้าไม่ใช่ทั้งหมด) คุณต้องประกาศตัวแปร ตัวอย่างเช่นใน C # ถ้ามันเป็นเขตข้อมูลจำนวนแล้ว

int PhoneNumber

ถ้าฉันใช้ภาษาอังกฤษปกติฉันไม่จำเป็นต้องประกาศPhoneNumberว่าintจะใช้มัน ตัวอย่างเช่นถ้าฉันขอให้แซมเพื่อนของฉันให้ฉันเขาบอกว่า:

"แซมให้ฉันด้วยหมายเลขโทรศัพท์"

ฉันจะไม่พูด

"Char (20) แซมให้ฉันโทรศัพท์เบอร์"

ทำไมเราต้องระบุชนิดข้อมูลเลย


83
นั่นเป็นเพราะภาษาอังกฤษมีการพิมพ์โดยนัย - ดังนั้นPhoneNumber ของคุณจึงถูกพิมพ์โดยนัยว่าPhoneNumber - มนุษย์ยังมีการจัดสรรหน่วยความจำแบบไดนามิก ... ;)
HorusKol

28
คุณและแซมรู้ว่าหมายเลขโทรศัพท์ประกอบด้วยตัวเลขและคุณจะประหลาดใจเมื่อพบจดหมาย ไม่จำเป็นต้องบอกคอมพิวเตอร์
Thorbjørn Ravn Andersen

16
และเมื่อฉันได้ยินตัวเลขเช่น 1-800-JIMBO ในภาพยนตร์ความคิดของฉันคือ: ตัวเลขนั้นเป็นอย่างไร Oo
muru

103
คุณไม่ควรประกาศโทรศัพท์ว่าเป็น int ในภาษาการเขียนโปรแกรมส่วนใหญ่จะเป็นการลบศูนย์นำหน้า
Aron_dc

25
@HorusKol: มนุษย์ไม่เพียง แต่จัดสรรหน่วยความจำแบบไดนามิก แต่ยังเป็นตัวเก็บขยะที่ไม่ได้รับการ
ปกป้อง

คำตอบ:


79

ในภาษาการเข้ารหัสส่วนใหญ่ (ถ้าไม่ใช่ทั้งหมด) คุณต้องประกาศตัวแปร

[ ... ]

ทำไมเราต้องระบุชนิดข้อมูลเลย

นี่เป็นคำถามสองข้อ:

  • ทำไมเราต้องประกาศตัวแปร
  • ทำไมเราต้องประกาศประเภท?

อนึ่งคำตอบของทั้งคู่ก็คือเราทำไม่ได้

มีภาษาการเขียนโปรแกรมแบบคงที่มากมายที่คุณไม่จำเป็นต้องประกาศชนิด คอมไพเลอร์สามารถอนุมานประเภทจากบริบทโดยรอบและการใช้งาน

ตัวอย่างเช่นใน Scala คุณสามารถพูดได้

val age: Int = 23

หรือคุณสามารถพูดได้

val age = 23

ทั้งสองจะตรงเทียบเท่า: เรียบเรียงจะอนุมานชนิดที่จะมาจากการแสดงออกของการเริ่มต้นInt23

ในทำนองเดียวกันในC♯คุณสามารถพูดอย่างใดอย่างหนึ่งเหล่านี้และพวกเขาทั้งสองหมายถึงสิ่งเดียวกันแน่นอน:

int age = 23;
var age = 23;

คุณลักษณะนี้เรียกว่าการอนุมานประเภทและหลายภาษานอกเหนือจาก Scala และC♯มี: Haskell, Kotlin, Ceylon, ML, F♯, C ++ คุณตั้งชื่อมัน แม้แต่ Java ก็มีการอนุมานรูปแบบ จำกัด

ในภาษาการเขียนโปรแกรมแบบไดนามิกตัวแปรไม่ได้มีประเภท ประเภทมีอยู่เฉพาะที่รันไทม์ไม่ใช่แบบคงที่ เฉพาะค่าและนิพจน์ที่มีประเภทและเฉพาะที่รันไทม์เท่านั้นตัวแปรไม่ได้มีประเภท

เช่นใน ECMAScript:

const age = 23;
let age = 23;

และสุดท้ายในหลาย ๆ ภาษาคุณไม่จำเป็นต้องประกาศตัวแปรเลย เช่นใน Ruby:

age = 23

ในความเป็นจริงตัวอย่างสุดท้ายนั้นใช้ได้ในภาษาการเขียนโปรแกรมจำนวนหนึ่ง ตัวอย่างของรหัสเดียวกันนี้จะใช้กับ Python ได้เช่นกัน

ดังนั้น,

  • แม้ในภาษาที่พิมพ์แบบคงที่ซึ่งตัวแปรมีประเภทคุณไม่จำเป็นต้องประกาศ
  • ในภาษาที่พิมพ์แบบไดนามิกตัวแปรไม่มีประเภทดังนั้นแน่นอนว่าคุณไม่สามารถประกาศได้
  • ในหลาย ๆ ภาษาคุณไม่จำเป็นต้องประกาศตัวแปร

2
อีกประการหนึ่งสำหรับการอธิบายทั้งการอนุมานประเภทและการพิมพ์แบบไดนามิก (การรวม
ภายหลัง

36
นี่เป็นข้อมูลที่ยอดเยี่ยมเกี่ยวกับความเข้าใจผิดหลังคำถาม แต่ยังคงทิ้งคำถามไว้ คำถามที่ถูกต้องมากขึ้นคือเหตุผลที่เราต้องระบุชนิดข้อมูลเมื่อประกาศตัวแปรในภาษาที่ต้องใช้? ทำไมพวกเขาถึงออกแบบมา? มีคำตอบที่ดีสำหรับคำถามนั้นและในขณะที่อธิบายอย่างละเอียดเกี่ยวกับทางเลือกจะขยายขอบเขตอันไกลโพ้นของ OP และดีมากซึ่งดูเหมือนจะไม่สมบูรณ์สำหรับฉัน
KRyan

7
@Kyan: ถ้าคุณต้องการรู้ว่าทำไมนักออกแบบภาษาบางคนเลือกภาษาที่ต้องการคุณจะต้องถามนักออกแบบภาษานั้นฉันกลัว ฉันไม่สามารถบอกคุณได้ว่าทำไมนักออกแบบของC♯ตัดสินใจเปรียบเทียบข้อสรุปประเภทและฉันไม่สามารถบอกคุณได้ว่าทำไมพวกเขาถึงเปลี่ยนใจในภายหลัง การออกแบบภาษานั้นมีความเห็นอย่างหนักและมักจะมีรสนิยม ถ้า OTOH คุณต้องการทราบเกี่ยวกับการแลกเปลี่ยนที่เฉพาะเจาะจงคำตอบนั้นโดยทั่วไปแล้วจะพิมพ์ใหม่ของประเภทและภาษาการเขียนโปรแกรมของ Prof. Pierce ซึ่งกว้างเกินไปสำหรับ Stack Exchange
Jörg W Mittag

2
JörgWMittag: ตามที่ @Kyan บอกไว้แล้วคำตอบ "คุณไม่จำเป็นต้อง" เป็นเรื่องที่น่าสนใจมาก (เห็นได้ชัดว่าเล็กน้อย - ภาษาหลายภาษาอนุญาตให้ละเว้นการประกาศประเภทในบางกรณี) คำถาม "ทำไมคุณต้องการประกาศประเภท" น่าสนใจกว่าและสะท้อนจิตวิญญาณของคำถามดั้งเดิมได้ดีกว่า (คำตอบของคุณทำให้ฉันนึกถึงเรื่องตลก: "เราอยู่ที่ไหน" - "คุณอยู่ในบอลลูนลมร้อน ! " ) คุณไม่จำเป็นต้องรู้ว่านักออกแบบของภาษาที่เฉพาะเจาะจงคิดอย่างไรในเวลานั้นเพื่อให้เหตุผลที่ดีบางประการแก่การประกาศประเภท
jfs

1
@Zaibis: auto i = 1 // i is inferred to type int, vector<int> vec; auto itr = vec.iterator(); // itr is inferred to type vector<int>::iteratorและอื่น ๆ หากคุณต้องการทราบว่ามันทำงานอย่างไรคุณสามารถค้นหาได้ในสเป็ค
Jörg W Mittag

53

เมื่อคุณใช้ภาษาธรรมชาติในการอ้างอิงข้อมูลมันไม่แม่นยำมากและโดยเฉพาะอย่างยิ่งไม่ได้สื่อสารกับผู้อื่นเกี่ยวกับความตั้งใจของคุณ ปัญหาที่คล้ายกันเกิดขึ้นเมื่อพยายามทำคณิตศาสตร์ในภาษาธรรมชาติมันไม่แม่นยำพอ

การเขียนโปรแกรมมีความซับซ้อน ข้อผิดพลาดนั้นง่ายเกินไป ประเภทเป็นส่วนหนึ่งของระบบการตรวจสอบที่ออกแบบมาเพื่อป้องกันสถานะของโปรแกรมที่ผิดกฎหมายโดยการตรวจสอบเงื่อนไขข้อผิดพลาด ภาษาที่แตกต่างกันใช้ประเภทต่างกัน: บางภาษาใช้ชนิดอย่างหนักเพื่อตรวจหาข้อผิดพลาดในเวลารวบรวม เกือบทุกภาษามีแนวคิดบางอย่างเกี่ยวกับชนิดที่เข้ากันไม่ได้เป็นข้อผิดพลาดรันไทม์ โดยปกติข้อผิดพลาดประเภทระบุข้อผิดพลาดของการเรียงลำดับบางอย่างในโปรแกรม เมื่อเราอนุญาตให้โปรแกรมดำเนินการต่อแม้จะมีข้อผิดพลาดเราก็อาจได้รับคำตอบที่แย่มาก เราต้องการหยุดโปรแกรมแทนที่จะรับคำตอบที่ไม่ดีหรือไม่ถูกต้อง

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

มันเป็นความจริงที่มนุษย์ (หลายคน) แยกแยะความแตกต่างระหว่างหมายเลขโทรศัพท์ในยุโรปสหรัฐอเมริกาและต่างประเทศได้อย่างง่ายดาย อย่างไรก็ตามคอมพิวเตอร์ไม่ได้ "คิด" จริง ๆ และถ้าหากบอกให้หมุนหมายเลขโทรศัพท์สหรัฐอเมริกาในยุโรปหรือในทางกลับกัน ตัวอย่างเช่นประเภทเป็นวิธีที่ดีในการแยกความแตกต่างระหว่างกรณีเหล่านี้โดยไม่ต้องสอนคอมพิวเตอร์ถึงวิธีการ "คิด" ในบางภาษาเราจะได้รับข้อผิดพลาดในการรวบรวมเวลาสำหรับพยายามผสมหมายเลขโทรศัพท์ในยุโรปบนระบบโทรศัพท์อเมริกา ข้อผิดพลาดนั้นบอกเราว่าเราจำเป็นต้องแก้ไขโปรแกรมของเรา (อาจแปลงหมายเลขโทรศัพท์เป็นลำดับการโทรระหว่างประเทศหรือโดยใช้หมายเลขโทรศัพท์ในยุโรปแทน) ก่อนที่เราจะพยายามเรียกใช้โปรแกรม

นอกจากนี้ในขณะที่คอมพิวเตอร์ไม่ได้คิดชื่อของฟิลด์หรือตัวแปร (เช่นphonenumber) จะไม่มีความหมายต่อคอมพิวเตอร์ สำหรับคอมพิวเตอร์ชื่อฟิลด์ / ตัวแปรนั้นเป็นเพียง "blah123" ลองคิดดูว่าโปรแกรมของคุณจะเป็นอย่างไรถ้าตัวแปรทั้งหมดเป็น "blahxxx" Yikes นั่นคือสิ่งที่คอมพิวเตอร์เห็น การระบุประเภทจะทำให้คอมพิวเตอร์มีความหมายของตัวแปรที่ไม่สามารถอนุมานได้จากชื่อเพียงอย่างเดียว

นอกจากนี้ @Robert พูดว่าในภาษาสมัยใหม่หลาย ๆ เราไม่จำเป็นต้องระบุประเภทมากที่สุดเท่าที่เราทำในสมัยก่อนเป็นภาษาเช่น C # ดำเนินการ "การอนุมานประเภท" ซึ่งเป็นชุดของกฎเพื่อกำหนดประเภทที่เหมาะสม สำหรับตัวแปรในบริบท C # ให้เฉพาะการอนุมานประเภทในตัวแปรท้องถิ่น แต่ไม่ได้อยู่ในพารามิเตอร์ที่เป็นทางการหรือฟิลด์คลาสหรืออินสแตนซ์


4
ส่วนที่น่าเศร้า: เป็นไปไม่ได้ที่จะอนุมานประเภทของสมาชิกที่สามารถเข้าถึงได้แบบสาธารณะ (เขตข้อมูลสาธารณะ, ลายเซ็นวิธีการสาธารณะ) เนื่องจากคุณไม่สามารถคาดการณ์เวลาและวิธีการที่จะใช้ นอกจากนี้คำอธิบายประกอบประเภทเป็นเอกสาร
Sergio Tulentsev

ฉันคิดว่าคุณควรเน้น / หนาบรรทัดนี้: Types are part of a system of checks that ...เนื่องจากมันเป็นการตอบรับ OP โดยตรงWhy do we have to specify data type at all?..
txtechhelp

หมายเหตุ: คุณตอบสมมติว่าภาษาที่ใช้ในการระบุประเภทนั้นสามารถหลีกเลี่ยงข้อผิดพลาดได้ดีกว่าภาษาโปรแกรมปกติของคุณ เห็นได้ชัดว่าไม่ใช่เช่นนั้นให้พิจารณาภาษาเทมเพลต C ++ ที่ทัวริงสมบูรณ์ (และอนุญาตให้แสดงการตรวจสอบข้อผิดพลาดจำนวนมาก) แต่แทบจะอ่านไม่ได้เมื่อเทียบกับภาษาทัวริงที่สมบูรณ์อื่น ๆ เช่น Haskell, Python และแม้แต่ส่วนอื่น ๆ C ++ เอง ถามตัวคุณเองว่าทำไมคุณไม่ใช้ภาษาการเขียนโปรแกรมเดียวกันเพื่อแสดงการตรวจสอบข้อผิดพลาดเหมือนกับส่วนที่เหลือของโปรแกรม (มีคำตอบที่ดีในบางกรณี แต่ไม่ใช่ทุกกรณี)
jfs

@SergioTulentsev ไม่เป็นความจริง - ใน F # คุณสามารถมีวิธีสาธารณะโดยไม่ต้องระบุประเภทของพวกเขาอย่างชัดเจน คอมไพเลอร์จะอนุมานชนิดจากการใช้ภายในเมธอด static member add x y = x + yตัวอย่างต่อไปนี้เป็นคำจำกัดความของวิธีการของประชาชนที่ถูกต้อง: member x.Append s = x.Text + s, ในกรณีแรกxและyจะถูกอนุมานว่าintเป็นเพราะการเพิ่ม ในกรณีที่สองพวกเขาจะเป็นสิ่งที่ถูกต้องขึ้นอยู่กับประเภทของx.Text- ถ้ามันเป็นstringแล้วก็sจะเป็นstringเช่นกัน ฉันยอมรับว่าคำอธิบายประกอบประเภทเป็นเอกสารแม้ว่า
Roujo

"ประเภทท้องถิ่นโดยปริยายประเภทอินเตอร์เฟซที่ชัดเจน" เป็นวิธีการที่จำนวนมากของโปรแกรมคนแม้ในภาษาเช่น Haskell ที่ช่วยให้คุณงด (เกือบ) ทุกประเภทขณะที่ยังมีคอมไพเลอร์สรุปประเภทที่เข้มงวด มีหลายคนที่ไม่คิดว่ามันน่าเศร้าเมื่อภาษาบังคับใช้การฝึกฝนนี้ (อย่างที่ C # ทำ)
Ben

29

นอกจากคำตอบอื่น ๆ แล้วมีสิ่งหนึ่งที่ควรรวมอยู่ด้วย จำไว้ว่าคอมพิวเตอร์เป็นเพียงบิต ว่าฉันให้คุณไบต์:

26 3A 00 FF

นั่นหมายความว่าอย่างไร มันเก็บไว้ด้วยวิธีนี้โดยคอมพิวเตอร์ แต่ไม่มีการตีความใด ๆ ก็เพียงบิต อาจเป็น 4 อักขระ ASCII อาจเป็นจำนวนเต็ม อาจเป็นบางไบต์ในอาร์เรย์ มันอาจเป็นส่วนหนึ่งของวัตถุ อาจเป็นตัวชี้ไปยังที่ที่วิดีโอแมวกำลังบัฟเฟอร์ ภาษาการเขียนโปรแกรมทั้งหมดจากชุดประกอบขึ้นไปจำเป็นต้องมีบางสิ่งบางอย่างเพื่อทราบวิธีการตีความบิตเพื่อให้พวกเขาทำการคำนวณที่มีความหมาย

และเนื่องจากคอมพิวเตอร์ไม่สามารถรู้ความหมายของบิตเหล่านั้นได้คุณจึงจำเป็นต้องแจ้งให้ทราบไม่ว่าจะเป็นคำอธิบายประกอบอย่างชัดเจนผ่านทางกลไกการอนุมานของประเภทที่กล่าวถึงในคำตอบอื่น ๆ


10
เป็นจริงเพียงพอ แต่เพื่อทำให้ใจของคุณสับสนจริงๆให้ตระหนักว่าคอมพิวเตอร์ไม่สามารถเข้าใจความหมายของบิตเหล่านั้นได้ - แม้ว่าคุณจะบอกคำอธิบายประกอบแบบอื่น ๆ ก็ตาม คำอธิบายของคุณจะเปลี่ยนเป็นเลขฐานสิบหกให้มากขึ้นเพื่อ "ชี้แจง" ตัวเลขฐานสิบหกตัวแรก ความสำคัญนั้นถูกสร้างขึ้นโดยผู้คนเพื่อนำความตั้งใจไปสู่อุปกรณ์อิเล็กทรอนิกส์และนำพวกเขาไปทำในสิ่งที่เราตั้งใจไว้ ตอนนี้ไปพูดว่า "ขอบคุณ" กับวิศวกร :)
Wildcard

1
ฉันใช้เวลาเขียนโปรแกรมบนเมนเฟรมเป็นเวลาหลายปี ด้วย PL / 1 คำตอบนี้สมเหตุสมผลอย่างมาก ค่อนข้างบ่อยเราจะใช้หน่วยเก็บข้อมูลตามตัวชี้ที่ถูกกำหนดเป็นที่อยู่ของตัวแปรอื่นของชนิดข้อมูลที่แตกต่างกันเพื่อเข้าถึงไบต์ในวิธีที่แตกต่างกัน ตัวอย่าง PL / 1 ไม่สนับสนุนฟิลด์ตัวเลขไบนารี่ 1 ไบต์ แต่เราจะสร้างตัวแปรตัวละคร 1 ตัวที่ที่อยู่เพื่อให้เราสามารถเก็บอาร์เรย์ 6 ไบต์ที่เก็บ 6 ฟิลด์ไบท์ไบต์เดียวได้ (ในกรณีนี้ทำให้เราสามารถบันทึกได้ 6 ไบต์ต่อที่อยู่ - ซึ่งเป็นสิ่งสำคัญเมื่อพื้นที่เก็บข้อมูลมีราคาแพง)
กระตุ้น

1
คอมพิวเตอร์สามารถเข้าใจความเป็นไปได้มากมาย แต่แม้กระทั่งคอมไพเลอร์ที่ฉลาดก็ต้องเข้าใจบริบท หมายเลข 0 หรือ "0" ไม่เหมือนกัน หรือสตริง "Dec 31" จะถูกสั่งก่อน "May 1" ถือว่าเป็น String แต่ไม่ใช่ถ้าถือเป็น Date หรือใช้เวลา 5/2 มันคือ 2 เป็นการป้อน แต่ 2.5 เป็นสองเท่า นอกจากนี้ประเภทนี้เป็นมาตรการรักษาความปลอดภัยสำหรับการแปลงที่ไม่ต้องการ Null, NaN และการปัดเศษหรือโอเวอร์โฟลว์อาจกลายเป็นปัญหา ภาษาที่แข็งแกร่งและพิมพ์แบบสแตติกมีข้อดีบางประการ ตัวอย่างเช่นคอมไพเลอร์ช่วยให้คุณตรวจพบปัญหาในขณะที่ refactoring
Borjab

1
@Borjab คุณหมายถึง "มันเป็น 2 เป็นจำนวนเต็ม " หรือไม่?
Richard Everett

1
@ RichardEverett แน่นอนว่าเป็น Lapsus ขอขอบคุณที่มาช้าในการแก้ไข
Borjab

23

คำตอบว่าทำไมคอมพิวเตอร์ต้องใช้ข้อมูลนี้จะทำอย่างไรกับข้อมูลแทน

ชื่อของ "ชนิดข้อมูล" เป็นการอ้างอิงถึงกฎที่ช่วยให้คอมพิวเตอร์จัดเก็บและดึงข้อมูลจากสถานะดิบของ 0 และ 1 ในหน่วยความจำคอมพิวเตอร์

ตัวอย่างเช่นอักขระ ASCII 8 บิตแบบปกติของคุณจะถูกเก็บไว้ในหน่วยความจำคอมพิวเตอร์ (RAM หรือ Disk) เป็น01000001(ตัวอักษรตัวพิมพ์ใหญ่ "A", รหัส ASCII 65) หรือ00001000(เครื่องหมายเปอร์เซ็นต์) หรือชุดใด ๆ ของ 0 และ 1 ใน 8 บิตเหล่านั้น

สำหรับตัวอย่างอื่นจำนวนเต็มแบบ 8 บิตที่ไม่ได้ลงชื่ออาจถูกเก็บเป็น00000101(หมายเลข 5) หรือ00001000(หมายเลข 8)

ขอให้สังเกตว่าการเป็นตัวแทนไบนารีของ 8 และอักขระ% อาจเหมือนกัน แต่พวกเขาหมายถึงสิ่งที่แตกต่างเพราะประเภทของพวกเขาจะแตกต่างกัน

แม้แต่ภาษาที่อนุมานชนิดข้อมูลพวกเขาอาจไม่มีกฎว่า "โปรแกรมเมอร์ทุกประเภทต้องแจ้งให้ทราบ" พวกเขามีกฎเช่น "ถ้าชุดอักขระของคุณอยู่ในเครื่องหมายคำพูดมันเป็นสตริง" และ กฎอื่น ๆ อีกมากมายสำหรับแต่ละประเภทข้อมูล

ดังนั้นแม้เหล่านี้ต้องการชนิดข้อมูลเพื่อให้เข้าใจถึงความหมายของ 0 และ 1 ดังนั้นพวกเขาจึงสามารถทำฟังก์ชั่นการต่อสตริงถ้าคุณพยายามที่จะ "เพิ่ม" สองตัวอักษรหรือเพิ่มจำนวนเต็มถ้าคุณพยายามที่จะเพิ่มจำนวนเต็มสองจำนวน .

ในเรื่องราวของคุณเช่นกันสมมติว่าคุณไม่ได้ขอหมายเลขโทรศัพท์จากแซม แต่แซมให้แผ่นกระดาษที่เขียนว่า "1123581321" ลงบนกระดาษ คุณคงไม่แน่ใจว่า Sam เป็นแฟนของหมายเลข Fibonacci แปดตัวแรกหรือว่าเป็นหมายเลขโทรศัพท์ ในการคาดเดาคุณจะต้องคำนึงถึงบริบทและตัวชี้นำที่คุณมีอยู่เช่นบางทีคุณอาจขอหมายเลขโทรศัพท์จาก Sam วันที่ผ่านมาหรือโน้ตบอกว่า "โทรหาฉัน" หรือถ้าคุณนับตัวเลขและค้นหา มันตรงกับรูปแบบของหมายเลขโทรศัพท์ส่วนใหญ่ เมื่อนั้นคุณจะรู้ว่ามันเป็นหมายเลขโทรศัพท์ที่คุณสามารถโทรหาและไม่ใช่ตัวเลขบางตัวที่คุณใช้เป็นเครื่องคิดเลข

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


3
นี่คือคำตอบที่ใกล้เคียงที่สุด ทุกอย่างเกี่ยวกับหน่วยความจำ คุณประกาศประเภทเพื่อให้คอมไพเลอร์รู้จำนวนหน่วยความจำของแอปพลิเคชันที่ควรร้องขอในขณะใช้งานจริง การรู้ว่าควรตีความบิตเป็นอย่างไรรอง
Greg Burghardt

@GregBurghardt จริง สำหรับการทำความเข้าใจบิตที่มีอยู่แล้วรวมถึงการวางบิตไว้ในตำแหน่งแรกหลังจากแปลงข้อมูลที่กำหนดให้เป็นไบนารีตามชนิดข้อมูล
Peeyush Kushwaha

10

ในบางภาษาคุณไม่จำเป็นต้องระบุชนิดข้อมูล

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

var name = "Ali"

ถูกพิมพ์ภายในเป็นสตริงเนื่องจากค่าล้อมรอบด้วยเครื่องหมายคำพูด

บางภาษาไม่ต้องการให้คุณประกาศตัวแปรเช่นกัน ตัวแปรจะถูกสร้างขึ้นเมื่อมีการใช้งานครั้งแรก อย่างไรก็ตามถือว่าเป็นแนวปฏิบัติที่ดีที่สุดในการประกาศตัวแปรของคุณโดยเฉพาะด้วยเหตุผลสำคัญหลายประการ ส่วนใหญ่เป็นเพราะการทำเช่นนั้นเป็นการแสดงออกถึงความตั้งใจของคุณได้ดีขึ้น


5
var name = "Ali"สไตล์เป็นจริงทั่วไปสำหรับทันสมัยแบบคงที่พิมพ์ภาษา ในภาษาที่พิมพ์แบบคงที่ประเภทจะถูกกำหนดไว้ที่การสร้าง แต่มันยังคงสามารถกำหนดได้โดยตัวกำหนดค่าเริ่มต้น คำจำกัดความของภาษาที่พิมพ์แบบไดนามิกคือชนิดที่แนบกับค่าไม่ใช่ตัวแปร การกำหนดค่าให้กับตัวแปรจึงเป็นการกำหนดประเภทของตัวแปรเช่นกัน
MSalters

@MSalters: ฉันทำการปรับถ้อยคำเล็กน้อย
Robert Harvey

5
ประชดนี่คือสิ่งนี้รวมถึง C # กับไวยากรณ์ที่แน่นอนนี้
Derek Elkins

1
@MSalters การกำหนดค่าให้กับตัวแปรจึงกำหนดประเภทของตัวแปรเช่นกัน หรือว่าตัวแปรนั้นไม่มีประเภทโดยธรรมชาติและล่ามจะพยายามใช้การดำเนินการใด ๆ กับค่าของตัวแปร มีภาษาใด ๆ พิมพ์แบบไดนามิกที่รหัสดังต่อไปนี้ (Javascript) จะไม่ได้รับอนุญาตvar x = 5; x = "";เพราะสาเหตุที่คำสั่งแรกxที่จะมีประเภท "หมายเลข" ที่เกี่ยวข้องกับx? การเรียงลำดับของความขัดแย้งกับพิมพ์แบบไดนามิก และถ้าไม่ประเภทที่เกี่ยวข้องกับตัวแปรมีผลกระทบอะไรนอกเหนือจากความสัมพันธ์ประเภทที่มีค่า?
Zev Spitz

1
@ZevSpitz: ระบบชนิดแรกไม่ได้ถูกพิมพ์แบบไดนามิก แต่ไม่ได้พิมพ์เลย ตัวอย่าง Javascript ของคุณไม่ได้ถูกพิมพ์แบบไดนามิกเพราะประเภท Number ไม่สามารถเปลี่ยนแปลงได้ ในภาษาที่พิมพ์แบบไดนามิกให้x = "";เปลี่ยนประเภทของ x เป็นสตริงแม้ว่าจะเป็นตัวเลขก่อนหน้านี้
MSalters

9

เพราะนั่นคือสิ่งที่การออกแบบภาษาระบุ ดังนั้นเพื่อตอบคำถามของคุณเราต้องดูเจตนาที่อยู่เบื้องหลังการพิมพ์อย่างชัดเจนในภาษาเช่น C # และ C ++ (เอาละ C # ทำเพราะ C ++ ทำเพราะ C ทำดังนั้นเราต้องดูความตั้งใจก่อนแล้ว)

ก่อนอื่นการพิมพ์ที่ชัดเจนและคงที่ให้ความเข้มงวดในการเขียนโค้ดการระบุตัวแปรให้เป็นจำนวนเต็มหมายความว่าคอมไพเลอร์และซอฟต์แวร์ควรแปลกใจและโยนข้อผิดพลาดเมื่อคุณกำหนดอักขระหรือสตริงให้กับตัวแปร การพิมพ์แบบไดนามิกสามารถทำให้เกิดอาการปวดหัวสำหรับเลินเล่อ (เพียงแค่ดูวิธี PHP หรือจาวาสคริปต์เพื่อความเป็นจริงของสิ่งต่าง ๆ เช่นอาร์เรย์และสตริงว่าง)

คุณสามารถมีสแตติกที่มีการพิมพ์โดยปริยาย - การเริ่มต้นตัวแปรเป็นสตริงหมายความว่าตัวแปรควรจะเป็นสตริงเท่านั้น แต่ความรู้สึกของฉันคือสิ่งนี้อาจทำให้เกิดปัญหาสำหรับมนุษย์ที่อ่านรหัส (ฉันมักจะสันนิษฐานการพิมพ์แบบไดนามิก )

นอกจากนี้ยังเป็นไปได้ในบางภาษาการเขียนบางอย่างเช่นรหัสเทียมนี้เพื่อเริ่มต้นคลาสจากอินพุตสตริง:

PhoneNumber phoneNumber = "(61) 8 8000 8123";

ประการที่สองการพิมพ์ที่ชัดเจนก็ไปด้วยการจัดสรรหน่วยความจำ intอยู่เสมอไบต์จำนวนมากดังนั้น PhoneNumberเป็นไบต์จำนวนมากดังนั้น คอมไพเลอร์สามารถกำหนดบล็อกหน่วยความจำขนาดที่เหมาะสมซึ่งสามารถนำมาใช้ในภายหลังโดยไม่ต้องดูว่าจะต้องใช้พื้นที่เท่าใดเมื่อคุณกำหนดค่า

PhoneNumber phoneNumber;
...
phoneNumber = "some value from somewhere";

ในที่สุดมันก็ขจัดความสับสน ... เป็น 123 จำนวนเต็มหรือจำนวนเต็มไม่ได้ลงนาม? พวกเขาต้องการจำนวนไบต์เท่ากัน แต่ค่าสูงสุดที่เก็บไว้ในตัวแปรของทั้งสองประเภทแตกต่างกันมาก ...

สิ่งนี้ไม่ได้บอกว่าชัดเจนดีกว่าโดยนัย - แต่การออกแบบภาษานั้นขึ้นอยู่กับตัวเลือกประเภทนี้และ C # จะทำงานแตกต่างจากการพิมพ์โดยนัย PHP และ javascript จะทำงานแตกต่างจากการพิมพ์ที่ชัดเจน


5

เพราะแซมฉลาดกว่าคอมไพเลอร์ ตัวอย่างเช่นเมื่อคุณบอกว่าให้หมายเลขโทรศัพท์ฉันคุณไม่ได้ระบุว่าคุณต้องการคำนำหน้าประเทศหรือรหัสพื้นที่ไม่ว่าจะเป็นหมายเลขงานที่ต้องใช้เฉพาะตัวเลข 4 หลักสุดท้าย นอกจากนี้ถ้าคุณขอหมายเลขของร้านพิซซ่าท้องถิ่นคุณจะสามารถจัดการกับคำตอบ "pizza4u"

แซมคิดออกมาจากบริบท ในขณะที่คอมไพเลอร์สามารถคิดออกจากบริบทแซมจะดีกว่าที่มัน (และมีความสามารถในการขัดจังหวะกระบวนการเพื่อขอคำชี้แจง)

มีวิธีการพื้นฐานสองแบบสำหรับประเภทและตัวแปรโดยที่ตัวแปรมีประเภทซึ่งในกรณีนี้การกระทำที่ไม่ได้รับอนุญาตจากประเภทนั้นเป็นสิ่งต้องห้ามและป้องกันการรวบรวมหรือค่ามีประเภทและการกระทำที่ไม่ได้รับอนุญาต ประเภทจะถูกจับที่รันไทม์

แต่ละวิธีมีข้อดีและข้อเสีย โดยทั่วไปตัวเขียนคอมไพเลอร์พยายามลดข้อเสียให้น้อยที่สุดและเพิ่มความได้เปรียบให้มากที่สุด ซึ่งเป็นสาเหตุที่ทำให้ C # เช่นอนุญาตvar phoneNumber = GetPhoneNumber();และจะอนุมานประเภทของหมายเลขโทรศัพท์จากลายเซ็นของ GetPhoneNumber นั่นหมายความว่าคุณต้องประกาศประเภทของวิธีการ แต่ไม่ใช่ตัวแปรที่รับผลลัพธ์ ในทางตรงกันข้ามมีคำใบ้ / บังคับใช้โครงการประเภทต่างๆสำหรับ javascript ทุกอย่างเป็นการแลกเปลี่ยน


3

มันเป็นเรื่องของวิธีการจัดเก็บข้อมูล การโต้ตอบกับแซมของคุณจะทำการเปรียบเทียบที่ดีขึ้นถ้าคุณถามเพื่อให้คุณสามารถเขียนลงไปได้ แต่มีกระดาษมูลค่าแปดตัวอักษรเท่านั้น

"แซมให้ฉันเบอร์โทรศัพท์"

"5555555555"

"โอ้ไม่ฉันหมดถ้าเพียง แต่ฉันรู้ก่อนเวลาเท่าไหร่ข้อมูลที่ฉันขอให้ฉันได้เตรียมดีกว่า!"

ดังนั้นภาษาส่วนใหญ่จะทำให้คุณประกาศประเภทดังนั้นมันจะรู้และเตรียมล่วงหน้า:

"แซมหมายเลขโทรศัพท์ยาวเท่าไหร่"

"สิบตัวอักษร"

"ตกลงแล้วให้ฉันได้รับกระดาษชิ้นใหญ่กว่าตอนนี้ให้ฉันหมายเลขโทรศัพท์"

"5555555555"

"เข้าใจแล้ว! ขอบคุณแซม!"

มันจะยิ่งสวยขึ้นเมื่อคุณดูวิธีพื้นฐานจริง ๆ ที่จัดเก็บข้อมูล หากคุณเป็นเหมือนฉันคุณมีสมุดบันทึกที่มีบันทึกเบ็ดเตล็ดตัวเลขเพิ่งเขียนลงไปไม่มีบริบทหรือฉลากสำหรับสิ่งใดและคุณไม่มีเงื่อนงำอะไรที่มันหมายถึงสามวันต่อมา นี่เป็นปัญหาสำหรับคอมพิวเตอร์หลายครั้งเช่นกัน ภาษาจำนวนมากมีประเภท "int" (int, long, byte, byte) และประเภท "float" (float, double) ทำไมจึงจำเป็น

ก่อนอื่นเรามาดูวิธีการเก็บจำนวนเต็มและแสดงโดยทั่วไปภายในคอมพิวเตอร์ คุณอาจทราบว่าในระดับพื้นฐานมันเป็นเลขฐานสองทั้งหมด (1 และ 0) Binary เป็นระบบตัวเลขที่ทำงานเหมือนกับระบบเลขฐานสิบของเรา ในทศนิยมคุณนับ 0 ถึง 9 (ด้วยเลขศูนย์นำโดยนัยที่ไม่ได้เขียน) จากนั้นคุณหมุนกลับไปที่ 0 และเพิ่มตัวเลขถัดไปเพื่อให้คุณมี 10 คุณทำซ้ำจนกว่าคุณจะหมุนจาก 19 ถึง 20 ทำซ้ำจนกว่าคุณจะเกลือกกลิ้งจาก 99 ถึง 100 และอื่น ๆ

ไบนารีไม่แตกต่างกันยกเว้นว่าแทนที่จะเป็น 0 ถึง 9 คุณจะนับ 0 ถึง 1 0, 1, 10, 11, 100, 101, 110, 111, 1000 ดังนั้นเมื่อคุณพิมพ์ 9 ในหน่วยความจำที่บันทึกไว้ในไบนารี เป็น 1001 นี่คือตัวเลขจริง มันสามารถเพิ่มลบคูณและอื่น ๆ ในรูปแบบที่แน่นอน 10 + 1 = 11. 10 + 10 = 100 (ม้วนมากกว่า 1 ถึง 0 และถือ 1) 11 x 10 = 110 (และเทียบเท่า 11 + 11 = 110)

ขณะนี้อยู่ในหน่วยความจำจริง (รวมถึงรีจิสเตอร์) มีรายการอาร์เรย์สิ่งที่คุณต้องการเรียกใช้เป็นบิต (อาจเป็น 1 หรือ 0 ') ถัดจากกันและกันซึ่งเป็นวิธีที่ทำให้บิตเหล่านี้จัดระเบียบอย่างมีเหตุผลเพื่อสร้าง จำนวนมากกว่า 1 ปัญหาคือคุณทำอะไรกับทศนิยม? คุณไม่สามารถใส่ชิ้นส่วนของฮาร์ดแวร์ในระหว่างสองบิตในการลงทะเบียนและมันจะเสียค่าใช้จ่ายมากเกินไปในการเพิ่ม "บิตบิต" ในแต่ละคู่ของบิต แล้วจะทำอย่างไรดี?

คุณเข้ารหัสมัน โดยทั่วไปแล้วสถาปัตยกรรมของ CPU หรือซอฟต์แวร์จะเป็นตัวกำหนดว่าจะทำอย่างไร แต่วิธีการทั่วไปคือการเก็บเครื่องหมาย (+ หรือ - โดยทั่วไป 1 เป็นค่าลบ) ในบิตแรกของการลงทะเบียนmantissa (หมายเลขของคุณเปลี่ยนไป อย่างไรก็ตามหลายครั้งจำเป็นต้องกำจัดทศนิยม) สำหรับจำนวน X บิตต่อไปนี้และเลขชี้กำลัง (จำนวนครั้งที่คุณต้องเลื่อน) สำหรับส่วนที่เหลือ มันคล้ายกับสัญลักษณ์ทางวิทยาศาสตร์

การพิมพ์ช่วยให้คอมไพเลอร์รู้ว่ากำลังดูอะไรอยู่ ลองนึกภาพว่าคุณเก็บค่า 1.3 ไว้ในการลงทะเบียน 1 เราจะมากับรูปแบบการเข้ารหัสแฟนซีของเราที่นี่ 1 บิตสำหรับการลงชื่อ 4 สำหรับ mantissa และ 3 สำหรับการยกกำลัง (1 บิตสำหรับการลงนาม 2 สำหรับขนาด) นี่เป็นจำนวนบวกดังนั้นสัญญาณจึงเป็นบวก (0) แมนทิสซาของเราจะเป็น 13 (1101) และเลขชี้กำลังของเราจะเป็น -1 (101 (1 สำหรับค่าลบ, 01 = 1)) ดังนั้นเราเก็บ 01101101 ใน register 1 ตอนนี้เราไม่ได้พิมพ์ตัวแปรนี้ดังนั้นเมื่อ runtime ไปใช้มันก็บอกว่า "แน่นอนนี่เป็นจำนวนเต็มทำไมไม่" ดังนั้นเมื่อมันพิมพ์ค่าที่เราเห็น 109 (64 + 32 + 8 + 4 + 1) ซึ่งเห็นได้ชัดว่าไม่ถูกต้อง

ไม่ใช่ทุกภาษาที่คุณจะต้องพิมพ์อย่างชัดเจน C # มีคำหลัก "var" ที่ทำให้ประเภทของตัวแปรถูกตีความในเวลารวบรวมและภาษาอื่น ๆ เช่น Javascript มีการพิมพ์แบบไดนามิกทั้งหมดจนถึงจุดที่คุณสามารถเก็บจำนวนเต็มในตัวแปรแล้วกำหนดให้เป็นบูลีนจากนั้น กำหนดอีกครั้งเพื่อสตริงและภาษาที่ติดตามได้ทั้งหมด

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


2

มีภาษาการเขียนโปรแกรมที่คุณไม่ต้องประกาศชนิดข้อมูลสำหรับตัวแปรของคุณ มีแม้แต่ภาษาโปรแกรมที่คุณไม่ต้องประกาศตัวแปรล่วงหน้า คุณสามารถใช้มันได้ทันที

ปัญหาของการไม่ประกาศชื่อตัวแปรคือถ้าคุณเผลอสะกดชื่อตัวแปรโดยไม่ได้ตั้งใจตอนนี้คุณได้สร้างตัวแปรใหม่ที่ไม่เกี่ยวข้องอย่างสมบูรณ์โดยไม่ได้ตั้งใจ ดังนั้นเมื่อคุณเรียกใช้โปรแกรมของคุณคุณไม่สามารถคิดออกว่าทำไมนรกตัวแปรที่คุณตั้งค่าทันใดนั้นมีอะไรอยู่ในนั้น ... จนกระทั่งหลังจากหลายชั่วโมงของการแก้จุดบกพร่อง, คุณรู้ว่าคุณพิมพ์ผิดชื่อพิลึก! ฮึ่ม !!

พวกมันสร้างมันขึ้นมาดังนั้นคุณต้องประกาศชื่อตัวแปรที่คุณจะใช้ก่อนหน้า และเมื่อคุณพิมพ์ชื่อไม่ถูกต้องคุณจะได้รับข้อผิดพลาดในการคอมไพล์เวลาซึ่งจะบอกคุณทันทีว่าข้อผิดพลาดอยู่ที่ไหนก่อนที่โปรแกรมของคุณจะทำงาน มันง่ายกว่านี้ไหม?

ข้อตกลงเดียวกันกับชนิดข้อมูล มีภาษาการเขียนโปรแกรมที่คุณไม่จำเป็นต้องประกาศสิ่งที่ควรจะเป็น หากคุณมีcustomerตัวแปรที่เป็นเพียงชื่อลูกค้าไม่ใช่วัตถุของลูกค้าทั้งหมดพยายามดึงที่อยู่ลูกค้าจากสตริงธรรมดาธรรมดา ... จะไม่ทำงาน จุดทั้งหมดของการพิมพ์แบบคงที่คือโปรแกรมจะไม่รวบรวม มันจะบ่นเสียงดังชี้ไปยังสถานที่ที่แน่นอนที่เป็นปัญหา นั่นเป็นมากเร็วกว่าใช้รหัสของคุณและพยายามที่จะคิดออกว่าทำไมนรกมันไม่ทำงาน

ทั้งหมดนี้เป็นคุณสมบัติในการบอกคอมไพเลอร์ว่าคุณตั้งใจจะทำอะไรจึงสามารถตรวจสอบสิ่งที่คุณทำจริง ๆและตรวจสอบให้แน่ใจ ที่ทำให้คอมไพเลอร์สามารถค้นหาข้อบกพร่องให้คุณโดยอัตโนมัติซึ่งเป็นเรื่องใหญ่

(ย้อนกลับไปในอดีตอันไกลโพ้นคุณไม่จำเป็นต้องประกาศรูทีนย่อยคุณเพียงแค่GOSUBไปที่หมายเลขบรรทัดเฉพาะหากคุณต้องการส่งผ่านข้อมูลระหว่างรูทีนย่อยคุณจะต้องตั้งค่าตัวแปรโกลบอลเฉพาะเรียกรูทีนย่อยของคุณ ตัวแปรเมื่อรูทีนย่อยกลับมา แต่นั่นทำให้ง่ายที่จะลืมค่าเริ่มต้นของพารามิเตอร์อย่างใดอย่างหนึ่งดังนั้นตอนนี้ภาษาการเขียนโปรแกรมที่ทันสมัยเกือบทั้งหมดต้องการให้คุณประกาศพารามิเตอร์ที่รูทีนย่อยใช้จริงเพื่อให้เราสามารถตรวจสอบได้ว่า )


1
ใน C ++ คุณสามารถใส่ "auto x = 1" และมันรู้ว่ามันเป็น int อัตโนมัติ y = 1.2; auto z = 'Z'; ฯลฯ
QuentinUK

@QuentinUK ใน C # คุณสามารถใส่var x=1ผลลัพธ์ที่คล้ายกัน แต่นั่นไม่ใช่อะไร ใน Haskell คุณสามารถเขียนโปรแกรมทั้งหมดของคุณโดยไม่มีลายเซ็นชนิดที่ทุกคน แต่มันคือทั้งหมดที่พิมพ์แบบคงที่และคุณยังคงได้รับข้อผิดพลาดถ้าคุณทำผิดพลาด ... (ไม่ตรงหลักแม้ว่า.)
MathematicalOrchid

@QuentinUK แต่ถ้าคุณเขียนfor (auto i=0; i<SomeStdVector.size(); ++i)linter ของคุณจะบ่นเพราะมันอนุมานว่าเป็นประเภทที่เซ็นชื่อแล้วและคุณทำการเปรียบเทียบกับประเภทที่ไม่ได้ลงชื่อ คุณต้องเขียนauto i=0ul(ใส่ข้อมูลประเภทไว้อย่างชัดเจนอีกครั้งดังนั้นควรเขียนsize_t i=0ตั้งแต่แรก)
dmckee

1

หากฉันใช้ภาษาอังกฤษปกติฉันไม่จำเป็นต้องประกาศว่า PhoneNumber ใช้งานได้ดี ตัวอย่างเช่นถ้าฉันขอให้แซมเพื่อนของฉันให้ฉันเขาบอกว่า:

"แซมให้ฉันด้วยหมายเลขโทรศัพท์"

ฉันจะไม่พูด>

"Char (20) แซมให้ฉันโทรศัพท์เบอร์"

ทำไมเราต้องระบุชนิดข้อมูลเลย

แวะไปที่MathOverflowหรือวิทยาศาสตร์คอมพิวเตอร์เชิงทฤษฎีและอ่านซักพักเพื่อให้เข้าใจว่ามนุษย์สื่อสารกับ alogrithms กันอย่างไรเมื่อพวกเขาต้องการที่จะประกันว่าไม่มีความเข้าใจผิด หรืออ่านมาตรฐานสำหรับภาษาการเขียนโปรแกรมผู้ใหญ่

คุณจะพบว่าการกำหนดประเภทของค่าที่อนุญาตให้กับคำหนึ่ง ๆนั้นเป็นส่วนหนึ่งของการฝึกฝนการสื่อสารที่แม่นยำอย่างแท้จริงแม้กระทั่งจากมนุษย์สู่มนุษย์

สิ่งที่คุณสังเกตเห็นคือการโต้ตอบแบบวันต่อวันนั้นเป็นเรื่องปกติและมนุษย์ก็ทนต่อความผิดพลาดได้ดังนั้นความเข้าใจผิดเกี่ยวกับหมายเลขโทรศัพท์จึงเป็นสิ่งที่หลีกเลี่ยงได้โดยความรู้ร่วมกันของผู้เข้าร่วม

คุณเคยลองใช้หมายเลขโทรศัพท์ของใครบางคนในประเทศอื่นบ้างไหม? พวกเขาบอกคุณอย่างชัดเจนหรือไม่ว่ากี่ครั้งที่จะผลักดันให้ศูนย์ถึงที่อยู่สากล? พวกเขาบอกรหัสประเทศของคุณกับคุณหรือไม่ คุณจำมันได้หรือเปล่า คุณคาดหวังตัวเลขกี่หลัก คุณได้รับมากี่ครั้ง คุณรู้วิธีการจัดกลุ่มตัวเลขหรือไม่ หรือแม้กระทั่งถ้าจัดกลุ่มมีความสำคัญ?

ทันใดนั้นปัญหาก็ยากขึ้นมากและคุณอาจต้องระมัดระวังมากขึ้นในการตรวจสอบอย่างชัดเจนว่าหมายเลขที่ได้รับนั้นเป็นที่เข้าใจในแบบที่ผู้ส่งหมายถึง


0

เหตุผลอีกประการหนึ่งสำหรับการประกาศประเภทคือประสิทธิภาพ ในขณะที่จำนวนเต็มสามารถเก็บไว้ใน 1 ไบต์หรือ 2 ไบต์หรือ 4 โปรแกรมที่ใช้ตัวแปรจำนวนมากอาจใช้หน่วยความจำที่จำเป็น 4 เท่าทั้งนี้ขึ้นอยู่กับสิ่งที่ทำ มีเพียงโปรแกรมเมอร์เท่านั้นที่รู้ว่าพื้นที่เก็บข้อมูลขนาดเล็กสามารถทำงานได้ดังนั้นเขาสามารถพูดได้โดยการประกาศประเภท

นอกจากนี้วัตถุที่พิมพ์แบบไดนามิกยังอนุญาตให้มีหลายประเภทที่เป็นไปได้ทันที นั่นอาจทำให้เกิดค่าโสหุ้ย "ภายใต้ประทุน" ทำให้โปรแกรมช้าลงเมื่อเทียบกับการยึดติดกับประเภทเดียวตลอด


0

จำนวนภาษาการเขียนโปรแกรมเริ่มต้น (โดยเฉพาะ Fortran) ไม่ต้องการให้คุณประกาศตัวแปรก่อนการใช้งาน

สิ่งนี้นำไปสู่ปัญหามากมาย สิ่งหนึ่งที่ชัดเจนจริงๆคือคอมไพเลอร์ไม่สามารถจับข้อผิดพลาดการพิมพ์ที่เรียบง่ายได้อีกต่อไป หากคุณมีรหัสที่ควรจะแก้ไขตัวแปรที่มีอยู่ แต่มีการพิมพ์ผิดคุณยังคงมีรหัสที่สมบูรณ์แบบที่เพิ่งสร้าง (และกำหนดค่าให้กับ) ตัวแปรใหม่:

longVariableName = 1

// ...

longVaraibleName = longvariableName + anotherLongVariableName

ทีนี้, ดูที่การแยกอย่างนี้, เมื่อฉันได้พูดถึงการพิมพ์ผิดเป็นสาเหตุของปัญหา, มันอาจจะง่ายที่จะค้นหาการพิมพ์ผิดและปัญหาที่นี่ ในโปรแกรมที่มีความยาวซึ่งสิ่งนี้ถูกฝังอยู่กลางรหัสอื่น ๆ มากมายมันง่ายกว่าที่จะพลาด

แม้ในปัจจุบันจะมีภาษาที่พิมพ์แบบไดนามิกจำนวนมาก แต่คุณยังสามารถพบปัญหาพื้นฐานเดียวกันได้อย่างง่ายดาย บางคนมีสิ่งอำนวยความสะดวกบางอย่างที่จะเตือนคุณถ้าคุณกำหนดให้กับตัวแปร แต่ไม่เคยอ่านมัน (ซึ่ง heuristically จับปัญหาบางอย่างเช่นนี้) ทั้งสองคนอื่นไม่มีสิ่งนั้น


0

เมื่อคุณประกาศตัวแปรใด ๆ จะมีการจัดสรรพื้นที่บางส่วนในหน่วยความจำ แต่เครื่อง (คอมพิวเตอร์ในกรณีนี้) ไม่รู้ว่าจะต้องจัดสรรพื้นที่สำหรับตัวแปรนั้นเท่าใด

ตัวอย่าง: - คุณสร้างโปรแกรมที่ขอให้ผู้ใช้ป้อนหมายเลขใด ๆ ในกรณีนี้คุณต้องระบุประเภทข้อมูลเพื่อเก็บหมายเลขนั้นมิฉะนั้นเครื่องไม่สามารถตัดสินด้วยตัวเองว่าควรจัดสรร2 ไบต์ หรือ 2 กิกะไบต์หากพยายาม ในการจัดสรรด้วยตัวเองมันอาจส่งผลให้การใช้หน่วยความจำไม่มีประสิทธิภาพในทางกลับกันถ้าคุณระบุประเภทข้อมูลในโปรแกรมของคุณจากนั้นหลังจากการรวบรวมเครื่องจะจัดสรรพื้นที่ที่เหมาะสมตามความต้องการ


นี้ไม่ได้ดูเหมือนจะนำเสนออะไรที่สำคัญกว่าจุดทำและอธิบายในก่อน 11 คำตอบ
ริ้น

1
ริ้นคุณควรอ่านคำตอบทั้งหมดอีกครั้งอย่างละเอียดและเห็นว่าฉันได้พยายามตอบคำถามนี้ในลักษณะที่ง่ายกว่ามากซึ่งคนเข้าใจได้ง่าย
Atul170294

ฉันเพิ่งตรวจสอบสามคำตอบล่าสุดที่โพสต์ประมาณหนึ่งชั่วโมงก่อนหน้านี้และทั้งสามดูเหมือนว่าจะเป็นจุดเดียวกันและต่อการอ่านของฉันอธิบายมันในลักษณะที่ง่ายกว่าที่นี่
gnat

แม้ว่าฉันไม่ได้ตอบสนองต่อรางวัลการโหวตของคุณ แต่ฉันคิดว่าคุณควรจะรู้อะไรสักอย่าง แต่คุณควรลบคำตอบเพราะอาจให้ข้อมูลที่ไร้ประโยชน์หรือไม่ถูกต้องและหากมีสิ่งใดที่น่ารังเกียจ คำตอบทั้งหมดที่มีข้อมูลที่มีประโยชน์ที่สุดและเกี่ยวข้องจะได้รับจำนวน upvotes ที่สูงขึ้นซึ่งเพียงพอที่จะแยกความแตกต่างระหว่างคำตอบคำตอบที่ดีและคำตอบที่ดีที่สุด กิจกรรมที่ไร้เดียงสาของคุณในการหาคำตอบโดยไม่มีเหตุผลอันใดจะทำให้ผู้อื่นที่ต้องการแสดงความคิดเห็นซึ่งพวกเขาคิดว่าอาจเป็นประโยชน์ต่อผู้อื่นด้วยเช่นกัน
Atul170294

1
คำตอบของคุณน่าจะถูกลดระดับลงเนื่องจากไม่ถูกต้อง ไม่จำเป็นต้องพิมพ์แบบคงที่เพื่อช่วยในการจัดการหน่วยความจำ มีหลายภาษาที่อนุญาตให้พิมพ์แบบไดนามิกและภาษา / สภาพแวดล้อมเหล่านั้นสามารถจัดการกับปัญหาการจัดการหน่วยความจำที่คุณพูดถึง
Jay Elston
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.