2016-08-14 19 views

Odpowiedz

11

Przeciwko Ven, w komentarzach w następstwie Perl 6 odpowiedzi na pytanie SO „Czy istnieje język z constrainable typów?”, Napisał "perl6 doesn't have dependant types" a później napisał „rodzaj zależny, chyba nie ... cóż, jeśli otrzymujemy rozstrzygające where s ... "w wymianie na # perl6. (Odpowiedź Larry'ego Walla był "what's a few halting problems among friends". Btw, zdecydowanie najlepszy sposób, aby uzyskać odpowiedź autorytatywny na wszystkich rzeczy Perl 6 jest poprosić TimToady poprzez # perl6.)

Dla Podsumowanie dla 'dependent-type' SO tag jest „zależne są typy typy zależne od wartości. " Perl 6 obsługuje typy zależne od wartości, więc jest to.

Dla Podsumowanie edycja na zmianę przez Awwaiid że Perl 6 dodanego do strony Wikipedii na Dependent Types mówi „Perl 6 ... ma nierozstrzygalny typów zależnych”.

Strona Wikipedia rozpoczyna się:

rodzaj zależny jest typem, którego definicja zależy od wartości. "Para liczb całkowitych" to typ. "Para liczb całkowitych, gdzie druga jest większa od pierwszej" jest typem zależnym z powodu zależności od wartości.

Oto jeden sposób, aby utworzyć typ wzdłuż tych linii w Perl 6:

subset LessMorePair of Pair where { $_.key < $_.value } 
subset MoreLessPair of Pair where { $_.key > $_.value } 

multi sub foo (  Pair) { " P" } 
multi sub foo (LessMorePair) { "LMP" } 
multi sub foo (MoreLessPair) { "MLP" } 

for 1 => 1, 1 => 2, 2 => 1 { say foo $_ } 

# P 
# LMP 
# MLP 

Czy to znaczy, że Perl 6 subset funkcja generuje typy zależne? Być może właśnie o tym myśli Awwaiid.

+0

Cóż, w takim sensie, że perl 6 ma „typy w zależności od wartości”, to tak pewnie. Zgodnie z tą definicją, C także to robi. Ale tylko posiadanie indeksowanych typów nie jest zbyt użyteczne. – Ven

+0

FWIW, [rozważałem również porwanie sparametryzowanych ról] (https://github.com/vendethiel/6meta-experiments/blob/master/church.pl), ale działa tylko wersja 'count' (która usuwa je w czasie wykonywania) .Role wymagałyby fazy "tworzenia instancji" (jak szablony C++), aby uzyskać coś podobnego do typów zależnych, ale tego nie ma w menu :-). – Ven

+0

@Ven To brzmi jak dopuszczalna definicja zależnego pisania może być czymś w rodzaju "wystarczająco użytecznej/ogólnej kompilacji w pełni rozstrzygającej typowej kontroli predykatów, które zależą od wartości", więc w 2017 r. Typy indeksowane w wanilii się nie liczą, ponieważ są nie jest uważany za przydatny lub wystarczająco ogólny, ale sprawdza typ, który w odpowiedni sposób wykorzystuje solwer SMT. Więc nawet jeśli P6 był taki, że kompilator mógł analizować klauzule "where" i zamieniać 'where Int | Str | Ograniczenie typu IntStr' do sprawdzania typu w czasie kompilacji (czy może to kiedykolwiek zrobić?), Nadal nie będzie zależne od wpisywania. Czy to jest blisko? – raiph

11

Prawdopodobnie tak, jako podzbiory są to typy, które mogą zależeć od arbitralnych warunków. Jednak system typów zostałby sklasyfikowany jako niesłuszny, ponieważ niezmienniki typu nie są egzekwowane.

zwłaszcza o zmiennej do kolumny jest tylko zaznaczone na zlecenie, to modyfikacje przedmiotu, które sprawiają, że wypadają z podzbioru doprowadzi do zmiennej trzymania przedmiotu nie powinien być w stanie, na przykład

subset OrderedList of List where [<=] @$_; 

my OrderedList $list = [1, 2, 3]; 
$list[0] = 42; 
say $list ~~ OrderedList; 

Możesz użyć jakiegoś kreatora meta-obiektu, aby system obiektowy automatycznie sprawdzał typ po wywołaniu dowolnej metody, umieszczając obiekty w przezroczystych obiektach wartowniczych.

Naiwny realizacja mogłaby wyglądać następująco:

class GuardHOW { 
    has $.obj; 
    has $.guard; 
    has %!cache = 
     gist => sub (Mu \this) { 
      this.DEFINITE 
       ?? $!obj.gist 
       !! "({ self.name(this) })"; 
     }, 
     UNBOX => sub (Mu $) { $!obj }; 

    method find_method(Mu $, $name) { 
     %!cache{$name} //= sub (Mu $, |args) { 
      POST $!obj ~~ $!guard; 
      $!obj."$name"(|args); 
     } 
    } 

    method name(Mu $) { "Guard[{ $!obj.^name }]" } 
    method type_check(Mu $, $type) { $!obj ~~ $type } 
} 

sub guard($obj, $guard) { 
    use nqp; 
    PRE $obj ~~ $guard; 
    nqp::create(nqp::newtype(GuardHOW.new(:$obj, :$guard), 'P6int')); 
} 

To spowoduje, że po nie:

my $guarded-list = guard([1, 2, 3], OrderedList); 
$guarded-list[0] = 42; 
+1

Zgadzam się z ogólnym sentymentem, chociaż ciężka zależna maszynistka (lub cokolwiek co jest zalecane dla typów zależnych) może sprzeciwić się temu, że typ nie jest sprawdzany w czasie kompilacji, więc twój przykład się nie liczy. Myślę, że wszystko zależy od interpretacji. – moritz

+0

Co powiedział @moritz. Środowisko wykonawcze jest un (i) wpisane, więc musi się zdarzyć podczas kompilacji. – Ven