ฉันสงสัยเกี่ยวกับต้นกำเนิดของ "การปล่อย" ที่ใช้ใน Lisp, Clojure และ Haskell มีใครรู้บ้างว่าภาษานั้นปรากฏในภาษาใดเป็นอันดับแรก
ฉันสงสัยเกี่ยวกับต้นกำเนิดของ "การปล่อย" ที่ใช้ใน Lisp, Clojure และ Haskell มีใครรู้บ้างว่าภาษานั้นปรากฏในภาษาใดเป็นอันดับแรก
คำตอบ:
ดีขั้นพื้นฐานมีLETสำหรับการกำหนดเป็นส่วนหนึ่งของไวยากรณ์จากจุดเริ่มต้นในปี 1964 เพื่อที่จะเกิดขึ้นก่อนการใช้letเสียงกระเพื่อมซึ่งคริสเจสเตอร์หนุ่มชี้ให้เห็นไม่ปรากฏว่าจนถึงปี 1970 ตามวิวัฒนาการของเสียงกระเพื่อม
ฉันไม่เชื่อว่า COBOL, Fortran หรือ ALGOL มีLETอยู่ในไวยากรณ์ของพวกเขาเช่นกัน ดังนั้นฉันจะไปกับพื้นฐาน
letพื้นฐานแล้วไม่มีความหมายที่ จำกัด ขอบเขต ดังนั้นคำตอบที่ถูกต้องน่าจะเป็นเช่น "มันปรากฏตัวครั้งแรกในภาษาอังกฤษก่อนศตวรรษที่ 12"
letในบริบทนี้ ( letx isบางสิ่งบางอย่างinที่แสดงออกต่อไปนี้) ปรากฏตัวครั้งแรกในตำราคณิตศาสตร์เป็นภาษาอังกฤษและนี่คือที่มาในการเขียนโปรแกรม ฉันไม่เห็นความแตกต่างระหว่างระบบที่เป็นทางการ - ภาษาคณิตศาสตร์ภาษาการเขียนโปรแกรมไม่อย่างอื่น - มันเหมือนกันหมด
equals isและใช่หลอกรหัสคือคำตอบที่ดีที่สุดจนถึง
ฉันต้องการที่จะเพิ่มมุมมองทางทฤษฎี: ในแลมบ์ดานิ่วคลาสสิกletเป็นเพียงน้ำตาล syntactic ตัวอย่างเช่น
let x = N in M
สามารถเขียนใหม่ได้อย่างง่ายดายเช่นเดียวกับ
(λx.M)N
ดังนั้นการปรากฏตัวครั้งแรกในภาษา (ฟังก์ชั่น) ต้นไม่น่าสนใจ
อย่างไรก็ตามมันมีความสำคัญอย่างยิ่งกับการประดิษฐ์ระบบประเภทHindley-Milnerและอัลกอริทึมการอนุมานแบบ ในระบบประเภทletนี้ขาดไม่ได้เพราะเป็น polymorphic (ซึ่งแตกต่างจากλ-abstraction ใน HM) ตัวอย่างเช่นลองพิจารณานิพจน์ง่าย ๆ นี้:
let id = λx . x in id id
นี่idคือ polymorphic, มันมีประเภท∀α.α → α, และดังนั้นid idการตรวจสอบประเภท - มันเป็นประเภทid id : τ → τสำหรับ arbitrary τ (สำหรับครั้งแรกที่idเรากำหนดτ → τให้αและครั้งที่สองที่idเรามอบหมายτให้α)
อย่างไรก็ตามเราไม่สามารถเขียนซ้ำได้โดยใช้λ abstraction และแอปพลิเคชัน การแสดงออก
(λid . id id)(λx.x)
ไม่ได้พิมพ์ตรวจสอบเพราะภายในนามธรรมλแรกidจะต้องกำหนดประเภท monomorphic id : σสำหรับσบางและไม่มีσเช่นที่เราสามารถนำไปใช้ในการid : σid : σ
คุณสามารถลองด้วยตัวเองใน Haskell ในขณะที่let id = \x -> x in id id :: t -> tการตรวจสอบประเภทการพิมพ์(\id -> id id)(\x -> x)ล้มเหลวด้วย
เกิดขึ้นตรวจสอบ: ไม่สามารถสร้างประเภทไม่สิ้นสุด:
t0 = t0 -> t0
ในอาร์กิวเมนต์แรกของidคือid
ในการแสดงออก:id id
ในการแสดงออก:\id -> id id
a[i] *(a + i) บทความ Wikipediaยังมีคำอธิบายที่ดี
letแนะนำ
letนำมาใช้เป็นคำถามเริ่มต้นด้วยฉันสงสัยเกี่ยวกับต้นกำเนิดของ "ให้" ...
เสียงกระเพื่อมเป็นภาษาที่เก่าแก่ที่สุดของเหล่านี้มี LET ในขณะนี้ แต่พื้นฐานเป็นคนแรกที่ได้รับเพราะเสียงกระเพื่อมได้รับมันมากในภายหลัง
ใน Ada Lovelace Analytical Engine (1843) - ไม่มี LET โปรแกรมดูเหมือนว่า:
N0 6 N1 1 N2 1 × L1 L0 S1 L0 L2 S0 L2 L0 CB?11 '
ในPlankalkül of Zuse (1943-45) โปรแกรมจะมีลักษณะดังนี้:
P1 max3 (V0[:8.0],V1[:8.0],V2[:8.0]) → R0[:8.0]
max(V0[:8.0],V1[:8.0]) → Z1[:8.0]
max(Z1[:8.0],V2[:8.0]) → R0[:8.0]
END
รหัสย่อถูกเสนอโดย John Mauchly ในปี 1949
X3 = ( X1 + Y1 ) / X1 * Y1
PL ระดับกลางของ Burks, 1950 ใช้สำหรับการมอบหมาย ->
Rutishauser ในปี 1952 ใช้ =>=
คอมไพเลอร์Böhms, 1952, ใช้แล้ว ->
ที่มหาวิทยาลัยแมนเชสเตอร์ Alick Glennie พัฒนาขึ้นAutocodeในช่วงต้นทศวรรษ 1950 รหัสแรกและคอมไพเลอร์ได้รับการพัฒนาในปี 1952 สำหรับคอมพิวเตอร์ Mark 1 ที่มหาวิทยาลัยแมนเชสเตอร์และถือเป็นภาษาโปรแกรมระดับสูงที่คอมไพล์เป็นครั้งแรก อีกครั้ง->สำหรับการมอบหมาย
Charles Adams, FORTRAN 0 ของกลุ่ม Backus, Autocode 2 ของ Brooker, ПП1ของ Lubimsky และ Kamynin; ทั้งหมดในปี 1954 อีกครั้ง=
BACAIC (Grems, Porter), 1954, *สำหรับการมอบหมาย!
Kompiler, ADES, 1955, =
ไอที, 1956, <-
FORTRAN, 1957, =
AT-3 (1956), คณิตศาสตร์ - มาติ (1957), อีกครั้ง=,
แต่ Flow-Matic ในปี 1957 มีการบ้านสองงานและทั้งสองเป็นคำพูด
TRANSFER a TO b และ MOVE a TO b
เครื่องจักรของ Bauer และ Samelson, 1957: =>
ขออภัยฉันไม่สามารถครอบคลุมทุกภาษาระหว่างปีพ. ศ
1957 - COMTRAN (forerunner to COBOL)
1958 - LISP
1958 - ALGOL 58
1959 - FACT (forerunner to COBOL)
1959 - COBOL
1959 - RPG
1962 - APL
1962 - Simula
1962 - SNOBOL
1963 - CPL (forerunner to C)
ไม่มี LET สำหรับการมอบหมาย หรือไม่ได้ในกรณีของ LISP
Dartmouth BASICเป็นภาษาต้นฉบับของภาษาการเขียนโปรแกรมพื้นฐาน รุ่นแรกแบบโต้ตอบได้ให้บริการแก่ผู้ใช้ทั่วไปในมิถุนายน 1964 ;
LET / = — assign formula results to a variable
ระหว่างสามคนนั้นเสียงกระเพื่อมก็มีก่อนแน่นอน Haskell เข้ามาในยุค 80 และ Clojure ในยุค 00 และletมีมานานก่อนวันที่ใดวันหนึ่ง :-)
เป็นไปได้ว่าเสียงกระเพื่อมเป็นภาษาได้คิดค้นมันฉันไม่สามารถรับรองได้ว่า แต่ฉันจะทำบางวิจัยและดู :-)
อัปเดต: ตามวิวัฒนาการของเสียงกระเพื่อม (ดูหน้า 46) กล่าวถึงว่าletถูกประดิษฐ์ขึ้นในยุค 70:
LET- สร้างแมโครขึ้นมาใหม่และสร้างใหม่ในพื้นที่แต่ละแห่ง - เป็นผู้มาสายในโลก MacLisp; ตาม Lisp Archive มันถูกดูดซึมย้อนหลังเป็น PDP-10 MacLisp จาก Lisp-Machine Lisp ในปี 1979 ในเวลาเดียวกันDEFMACROและDEFUNไวยากรณ์อาร์กิวเมนต์Lisp Machine ที่ซับซ้อน
ยังไม่ตอบว่ามันถูกประดิษฐ์ในภาษาอื่นก่อนหน้านี้แน่นอน แต่ยังเป็นจุดข้อมูลอื่น :-)
ครั้งแรกที่ปรับปรุงโครงการรายงาน AIM-452 จากมกราคม 1978 LETมี หน้า 9
โปรดทราบว่า Lisp ใช้โครงสร้างที่แตกต่างกันก่อนหน้านี้PROGเพื่อแนะนำตัวแปรท้องถิ่น
(let ((a 1)
(b 1))
(+ a b))
จะถูกเขียนก่อนหน้านี้ประมาณว่า
(prog (a b)
(setq a 1)
(setq b 1)
(+ a b))
letกำหนดขอบเขตคำศัพท์ในภาษา Lisp เสมอหรือไม่
letจะเก่าแก่เท่าศัพท์ขอบเขต (Scheme, '75) และใช้เวลาสักครู่สำหรับการกำหนดขอบเขตคำศัพท์เพื่อให้ได้รับการยอมรับดังนั้นฉันเดาว่ากรณีแรกของการletอยู่ในบริบทของ Lisps แบบไดนามิก วันนี้ Emacs Lisp ยังคงมีขอบเขตแบบไดนามิกตามค่าเริ่มต้นด้วยlambdaและlet(น้ำตาลหลังสำหรับอดีตอยู่แล้ว) ผูกพารามิเตอร์ของพวกเขาแบบไดนามิก