Tür teorisinde doğru terminoloji: türler, tür yapıcılar, türler / türler ve değerler


14

Önceki bir sorunun cevabında , belirli yapılar için doğru terminoloji hakkında küçük bir tartışma başladı. Bunu açıkça ele alacak bir soru bulamadığım için ( bu ya da bunun dışında , doğru olanı değil), bu yeni soruyu yapıyorum.

Şüpheli terimler ve ilişkileri şunlardır: tür, tür yapıcı, tür parametresi, türler veya türler ve değerler .

Ayrıca wikipedia'yı tip teorisi için kontrol ettim , ama bu da pek açıklanmadı.

İyi bir referans cevabı almak ve kendi anlayışımı kontrol etmek için:

  • Bunlar nasıl doğru tanımlanır?
  • Bunların her biri arasındaki fark nedir?
  • Birbirleriyle nasıl ilişkilidir?

Yanıtlar:


13

Tamam, birer birer gidelim.

Değerler

Değerler, programların değerlendirdiği ve dengelediği somut veri parçalarıdır. Hiçbir şey fantezi, bazı örnekler olabilir

  • 1
  • true
  • "fizz buzz foo bar"

Türleri

Bir tür için güzel bir açıklama "bir değer için sınıflandırıcı" dır. Tür, bu değerin çalışma zamanında ne olacağı, ancak derleme zamanında gösterileceği hakkında biraz bilgi içerir.

Örneğin bunu bana söylemek eğer e : boolderleme sırasında ve bunu anlarsınız eya olduğu trueveya falseçalışma zamanı sırasında, başka bir şey! Türler değerleri böyle güzel bir şekilde sınıflandırdığından, bu bilgileri programınızın bazı temel özelliklerini belirlemek için kullanabiliriz.

Örneğin, eklemenizi eve e'ne zaman e : intve ne zaman görüyorsanız e' : String, o zaman bir şeyin biraz kapalı olduğunu biliyorum! Aslında bunu işaretleyebilir ve derleme zamanında "Hey, bu hiç mantıklı değil!"

Daha güçlü bir tip sistemi, daha ilginç değerleri sınıflandıran daha ilginç tiplere izin verir. Örneğin, bazı işlevleri ele alalım

f = fun x -> x

Oldukça açık f : Something -> Something, ama ne olmalı Something? Sıkıcı bir tip sistemde, keyfi bir şey belirtmeliyiz Something = int. Daha esnek bir tip sistemde,

f : forall a. a -> a

Yani "Herhangi için demek ki a, fbir harita abir etmek a". Bu fdaha genel olarak kullanalım ve daha ilginç programlar yazalım.

Dahası, derleyici, verdiğimiz sınıflandırıcıyı gerçekten tatmin edecek kontrol edecek, eğer f = fun x -> truebir hata varsa ve derleyici bunu söyleyecektir!

Bir tldr olarak; tür, bir ifadenin çalışma zamanında olabileceği değerler üzerinde bir derleme süresi kısıtlamasıdır.

Türü Yapıcı

Bazı türler birbiriyle ilişkilidir. Örneğin, tamsayıların listesi dize listesine çok benzer. Bu neredeyse sorttamsayıların sortdizeler için nasıl olduğu gibidir . Farklılıkları genelleştirerek ve talep üzerine inşa ederek bu hemen hemen aynı türleri inşa eden bir fabrika hayal edebiliriz. Bir tip yapıcı budur. Türlerden türlere bir işlev gibidir, ancak biraz daha sınırlıdır.

Klasik örnek genel bir listedir. İçin bir tür oluşturucu yalnızca genel tanımdır

 data List a = Cons a (List a) | Nil

Şimdi Listbir türü ao türdeki değerler listesiyle eşleyen bir fonksiyon ! Java topraklarında bunlara belki de "jenerik sınıflar" denir.

Tür Parametreleri

Bir tür parametresi yalnızca bir tür yapıcısına (veya işlevine) aktarılan türdür. Tıpkı değer düzeyinde olduğu gibi , tıpkı bir tür parametresinin nasıl olduğu gibi foo(a)bir parametreye sahip olduğunu söyleyebiliriz .aList aa

Çeşitleri

Türler biraz zor. Temel fikir, bazı türlerin benzer olmasıdır. Örneğin, tüm ilkel türleri java var int, char, float... hangi tüm uslu onlar aynı "türü" var sanki. Dışında, türlerin sınıflandırıcılarından söz ederken, sınıflandırıcı türlerini adlandırırız. Yani int : Prim, String : Box, List : Boxed -> Boxed.

Bu sistem, tıpkı türlerin değerleri nasıl yönettiği gibi, ne tür türleri kullanabileceğimiz konusunda güzel somut kurallar verir. Söylemek saçma olurdu

 List<List>

veya

 List<int>

Java bu yana Listkullanmak için somut bir tür uygulanması gerektiğinden! Onların türlerine bakarsak List : Boxed -> Boxedve o zamandan beri Boxed -> Boxed /= Boxed, yukarıdaki tür bir hatadır!

Çoğu zaman türleri gerçekten düşünmüyoruz ve sadece "sağduyu" olarak ele alıyoruz, ancak meraklı tip sistemleri ile düşünmek önemli bir şey.

Şimdiye kadar söylediğim şeyin küçük bir örneği

 value   : type : kind  : ...
 true    : bool : Prim  : ...
 new F() : Foo  : Boxed : ...

Wikipedia'dan Daha İyi Okuma

Bu tür bir şeyle ilgileniyorsanız, iyi bir ders kitabı yatırmanızı şiddetle tavsiye ederim. Tip teorisi ve PLT genel olarak oldukça geniştir ve tutarlı bir bilgi tabanı olmadan (veya en azından ben) aylarca hiçbir yere gitmeden dolaşabilirsiniz.

En sevdiğim kitaplardan ikisi

  • Türleri ve Programlama Dili - Ben Pierce
  • Programlama Dillerinin Pratik Temelleri - Bob Harper

Her ikisi de az önce bahsettiğim şeyleri anlatan mükemmel kitaplar ve çok daha güzel, iyi açıklanmış detaylar.


1
Türler kümeler mi? "Sınıflandırıcıyı" daha iyi seviyorum, ama bunun ne anlama geldiğini açıklamıyorsunuz ve bir türün ne olduğunu iyi bir şekilde anlamadan, cevabınızın geri kalanı düşüyor.
Robert Harvey

@RobertHarvey Şimdi nasıl görünüyor, setlerden bahsederim :)
Daniel Gratzer

1
Çok daha iyi ....
Robert Harvey

@RobertHarvey Türlerin görünümünü sezgisel olarak ayarladım. intJava'daki tür , 2 ^ 64 farklı değerden oluşur. Alt tipler dahil edildiğinde setlerle analoji bozulur, ancak özellikle cebirsel veri türlerini düşündüğünüzde yeterince iyi bir başlangıç ​​sezgisi vardır (örneğin, iki tür bir birleşim her iki türden herhangi birini içerebilir; bu kümelerin birleşimi) .
Doval

@Doval: Bir Müşteriyi tanımlayan bir sınıf yazarsam, büyük olasılıkla bir "müşteri kümesini" temsil edecektir, çünkü bir örnek koleksiyonu yapacağım. Ancak bir Müşterinin bir Tür olduğunu söylemek, çünkü bir müşteri kümesini tanımlamak bir totolojidir; çok açık görünüyor. Daha ilginç olan, bir Müşteri türünün bir müşterinin özelliklerini tanımlamasıdır . Bunu açıklamak için "set" kullanmak aslında olduğundan daha soyut ... gibi görünüyor. Belki bir matematikçi değilseniz.
Robert Harvey

2

Bunlar nasıl doğru tanımlanır?

Katı, akademik matematiksel destek ile doğru bir şekilde tanımlanırlar, ne oldukları, nasıl çalıştıkları ve nelerin garanti edildiği hakkında güçlü iddialar sağlarlar.

Ancak programcıların bunu büyük ölçüde bilmelerine gerek yok. Kavramları anlamalılar.

Değerler

Her şey oradan inşa edildiğinden, değerlerle başlayalım. Değerler, hesaplamada kullanılan verilerdir. Yaklaşıma bağlı olarak, herkesin bildiği değerlerdir: 42, 3.14, "Şimdi nasıl kahverengi inek", personel için Jenny'nin Muhasebe, vb.

Değerlerin diğer yorumları sembollerdir . Çoğu programcı bu sembolleri numaralandırmanın "değerleri" olarak bilir. Leftve Rightnumaralandırma için sembollerdir Handedness(çok yönlü insanları ve balıkları görmezden gelmek).

Uygulamadan bağımsız olarak, değerler, hesaplama yapmak için dilin birlikte çalıştığı farklı şeylerdir.

Türleri

Değerlerle ilgili sorun, tüm hesaplamaların tüm değerler için yasal olmamasıdır. 42 + goatgerçekten mantıklı değil.

Burada türler devreye giriyor. Türler, değerlerin alt kümelerini tanımlayan meta verilerdir. Yukarıdaki Handednessnumaralandırma buna iyi bir örnektir. Bu tür "yalnızca Leftve Rightburada kullanılabilir " diyor . Bu, programların belirli işlemlerin hataya neden olacağını çok erken belirlemesini sağlar.

Dikkate alınması gereken bir başka pratik kullanım, kaputun altında bilgisayarların baytlarla çalıştığıdır. Bayt 42, 42 sayısı anlamına gelebilir veya * karakteri anlamına gelebilir veya Muhasebe'den Jenny anlamına gelebilir. Türler de (pratik kullanımda, teorik olarak çok fazla değil), bilgisayarlar tarafından kullanılan temel bayt koleksiyonunun kodlamasını tanımlamaya yardımcı olur.

Çeşitleri

Ve işte orada biraz dışarı çıkmaya başlıyoruz. Bir programlama dili tipini kasteder bir değişken olduğunda yani, ne tür mu o var?

Örneğin Java ve C # 'da, türü vardır Type(türü Typeolan, ... ve benzeri tüm yol boyunca). Bu, türlerin ardındaki kavram . Bazı dillerde, Java ve C # 'dan bir Type değişkeni ile biraz daha faydalı şeyler yapabilirsiniz. Bu durum gerçekleştiğinde söylemek yararlı olur "Ben bir Tür Bir değer istiyoruz ama aynı zamanda bazı olduğu tür bir IEnumerable<int>". Sürpriz! Çeşitleri.

Çoğu programcı Java ve C # genel kısıtlamaları gibi türleri düşünebilir. Düşünün public class Foo<T> where T: IComparable{}. Çeşitleri olan bir dilde, T: kindOf(IComparable)değişken beyan yasal hale gelir; sadece sınıf ve işlev bildirimlerinde yapabileceğiniz özel bir şey değil.

Türü Konstrüktör

Belki de malum tip tanımına sade türleri için kurucular . "Ama bir tür oluşturmak nasıl? Tipleri sadece vardır .". Eh ... çok değil.

Ayrıca şaşırtıcı olmayan bir şekilde, herhangi bir bilgisayar programının kullanacağı tüm farklı faydalı değer alt kümelerini oluşturmak oldukça zordur . Tür yapıcılar, programcıların bu alt kümeleri anlamlı şekilde "oluşturmalarına" yardımcı olmak için çalışır.

Bir tür kurucusu en yerde, örneğin bir dizi tanımı: int[4]. Burada , 4 girişli bir s 4dizisi oluşturmak için değeri kullanan tür yapıcısını intbelirtiyorsunuz. Farklı bir giriş türü belirttiyseniz, farklı bir çıktı türü alırsınız.

Jenerikler, girdi olarak başka bir tür alan başka bir tür yapıcı biçimidir.

Birçok dilde P -> R, türü alan Pve türü döndüren bir işlevi temsil eden bir tür oluşturmak gibi bir tür yapıcısı vardır R.

Şimdi, bağlam "bir tür döndüren işlev" bir tür yapıcı olup olmadığını belirler. Benim (kuşkusuz sınırlı) deneyimlerime göre, satır "derleme zamanında bu tür kullanabilirsiniz?". Evet? Tip yapıcı. Hayır? Sadece bir fonksiyon.

Türü Parametresi

Yani Type Constructors'a iletilen parametreleri hatırlıyor musunuz? Tip Oluşturucu ortak şeklidir beri Bunlar genellikle, Tip Parametreler olarak bilinen konum Type[param]veya Type<param>.


1
'Çeşitler' bölümünü açıklayabilir / genişletebilir misiniz? Haskell'de bir türün bir türü vardır *, bir tür yapıcısının (bir argümanla) bir türü vardır * -> *. (Num a) => a("Tip sınıfının abir örneği olan herhangi bir tür" anlamına gelir) gibi kısıtlamalar Numkendileri tür değildir. Tip sınıfı Numbir 'tür' değil, bir türdür * -> Constraint. Haskell 'tür' fikrini (tip teorisindeki türlerle yakından ilişkili olduğunu varsayıyorum) verdiğiniz örneklerle ilişkilendirmekte zorlanıyorum.
John Bartholomew

Ben GHCi en demeliyim :kindkomut tür verir Numolarak * -> Constraint. Bu GHC'ye özgü olabilir, bilmiyorum.
John Bartholomew

@JohnBartholomew - Haskell Çeşitleri daha çok "Tip Oluşturucular için imzalar" dır. Ne yazık ki, Haskell'im neredeyse ayrıntılar hakkında çok fazla konuşabileceğim noktaya gelmiyor.
Telastyn
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.