Dlaczego Typescript używa słowa kluczowego „export”, aby upublicznić klasy i interfejsy?

138

Podczas zabawy z Typescriptem zdałem sobie sprawę, że moje klasy w modułach (używane jako przestrzenie nazw) nie były dostępne dla innych klas, chyba że napiszę exportprzed nimi słowo kluczowe, takie jak:

module some.namespace.here
{
   export class SomeClass{..}
}

Więc teraz mogę użyć powyższego kodu w ten sposób:

var someVar = new some.namespace.here.SomeClass();

Zastanawiałem się jednak, dlaczego to słowo kluczowe jest używane, a nie tylko publicsłowo kluczowe, które jest używane na poziomie metody do oznaczenia, że ​​metoda lub właściwość powinny być dostępne z zewnątrz. Dlaczego więc nie użyć tego samego mechanizmu, aby uczynić klasy, interfejsy itp. Zewnętrznie widocznymi?

Dałoby to wynikowy kod, taki jak:

module some.namespace.here
{
   public class SomeClass{..}
}
Grofit
źródło

Odpowiedzi:

179

Głównym powodem jest to, że exportpasuje do planów ECMAScript. Można argumentować, że „powinni byli użyć wyrażenia„ eksport ”zamiast„ publiczne ”, ale poza tym, że„ eksport / prywatny / chroniony ”jest słabo dopasowanym zestawem modyfikatorów dostępu, uważam, że istnieje subtelna różnica między nimi, która to wyjaśnia .

W TypeScript oznaczenie elementu członkowskiego klasy jako publiclub privatenie ma wpływu na wygenerowany JavaScript. Jest to po prostu narzędzie czasu projektowania / kompilacji, którego możesz użyć do zatrzymania kodu TypeScript przed dostępem do rzeczy, których nie powinien.

Za pomocą exportsłowa kluczowego JavaScript dodaje linię, aby dodać wyeksportowany element do modułu. W przykładzie: here.SomeClass = SomeClass;.

Tak więc, koncepcyjnie, widoczność jest kontrolowana przez narzędzia publici privatedotyczy tylko narzędzi, podczas gdy exportsłowo kluczowe zmienia dane wyjściowe.

Fenton
źródło
1
Dzięki za informację, zakładam, że decyzja była taka, jak mówisz, aby uniknąć konieczności sprawdzania kontekstu słowa kluczowego, co jest wstydem, ponieważ wydaje się, że jest to coś, co potknie kilka osób i naprawdę nie ma logicznej różnicy w zachowaniu tego, czego oczekujesz od opinii publicznej, po prostu ułatwia ich wdrożenie.
Grofit
Dzięki za to. Oszczędza mi ciągnięcia za włosy.
Kent Aguilar
1
Jest to konieczne, jeśli używasz modułów. Jeśli Twoja aplikacja jest skierowana na większą stronę, moduły są zwykle lepszym wyborem niż tworzenie dużych pakietów / ładowanie wszystkich plików z góry.
Fenton
@Fenton Czy nie chodziło Ci o to, że „mógłbyś argumentować, że powinni użyć słowa„ public ”zamiast„ export ”?
Alan Evangelista
@AlanEvangelista, możesz z pewnością argumentować to w ten sposób, zwłaszcza jeśli twoim tłem była Java / C #, a nie JavaScript.
Fenton
51

Kilka rzeczy do dodania do odpowiedzi Steve'a Fentona:

  • export już oznacza dwie różne rzeczy (w zależności od tego, czy jest na najwyższym poziomie, czy nie); co oznacza, że ​​jedna trzecia jest prawdopodobnie gorsza niż dodanie public/private
  • Na pewno nie ma to na celu ułatwienia implementacji; dodatkowa złożoność publicvs exportjest trywialna. Zmieniliśmy już kilka słów kluczowych; to nie jest trudne.
  • Domyślna widoczność członków klasy musi być publiczna, aby była zgodna z propozycją klasy ES6, dlatego potrzebujemy słowa kluczowego wskazującego „niepubliczne”. Nie ma odpowiedniego antonimu do export( unexport??), więc privatejest to logiczny wybór. Gdy już to zrobisz private, byłoby szaleństwem nie wybierać publicswojego odpowiednika
  • Użycie exportdo modyfikacji widoczności w modułach wewnętrznych jest najlepszym przypuszczeniem wyrównania z modułami ES6
Ryan Cavanaugh
źródło
1
dziękuję za dodatkowe informacje, całkowicie zgadzam się z tym, że na poziomie członków są publiczne / prywatne, po prostu uważam, że to dziwne, że nie jest wystarczające dla wszystkich poziomów dostępu. Jest to jednak osobista opinia, a słowo kluczowe jest słowem kluczowym, chciałem tylko dowiedzieć się więcej.
Grofit
5
Redaguję moje bezczelne stwierdzenie o łatwości wdrożenia i oferuję +1 jako przeprosiny :)
Fenton
2
Zgadzam się z częścią tego, co mówisz, ale nie zgadzam się ze stwierdzeniem „Nie ma odpowiedniego antonimu do eksportu” - „import” jest antonimem i jest tym, czego używa TypeScript, kiedy definiujesz klasę eksportowalną, wtedy zaimportuj go do innych plików export class User { name: string } Inny plik: import {User} from ""./the_file_path_to_the_user_class; zobacz sekcję 3.3 dokumentacji języka ojczystego
Adam Diament
3
W jaki sposób użycie importokreślenia „ta wartość nie jest eksportowana ” byłoby odpowiednim użyciem słowa kluczowego?
Ryan Cavanaugh
6
„Nie ma odpowiedniego antonimu do eksportu (niewyeksportowanie ??)” - odpowiednim antonimem do eksportu powinno być embargo.
rsp