eGospodarka.pl

eGospodarka.plGrupypl.comp.www › TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
Ilość wypowiedzi w tym wątku: 10

  • 1. Data: 2019-09-04 22:11:10
    Temat: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    Witam,

    Biję się z myślami czy nie przesiąść się z JS ES6 na TypeScript. Właśnie
    testuję pod PHPStorm'em edycję i transkompilację TS i działa ten
    mechanizm wyśmienicie. Ucieszony tym zabrałem się za pierwszy skrypt i
    ... poległem na podstawach. Stworzyłem dwie klasy jako moduły) Test i Test2:

    abstract class Test {
    private _message: string;

    protected printMessage() {
    console.log(this._message);
    }

    protected constructor(message: string) {
    this._message = message;

    }
    }

    export default Test;

    *****************************************

    import Test from "./Test";

    class Test2 extends Test{
    private _message: string;

    constructor(message:string) {
    super("dupa");
    this._message = message;
    }

    execute() {
    console.log(this._message);
    this.printMessage();
    }
    }

    let demo = new Test2("my message");
    demo.execute();

    Zadeklarowałem _message jako zmienną prywatną w obu klasach i... powstał
    konflikt! Transkompilator nie poradził sobie z tym. Oczekiwałbym
    samoczynnej zmiany nazwy funkcji by w wyjściowym JS nie było konfliktów.
    Zatem jak żyć? :-) To samo dotyczy metod. Te prywatne zwalczają się
    zamiast być niezależnymi w każdej z klas.

    Póki co nie dostrzegam wielkich korzyści z przejścia na TS. Aby uzyskać
    wpełni prywatne zmienne, muszę ręcznie rzeźbić kod na symbolach - jak w
    natywnym JS. Jedynie IDE nieco ułatwi programowanie ukrywając to, co
    prywatne i czasem przypilnuje typów (ale tylko przy jawnych
    podstawieniach). Czy zatem warto bawić się w TS?

    --
    Pozdrawiam,
    Marek


  • 2. Data: 2019-09-05 05:54:57
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Szyk Cech <s...@s...pl>

    Na pewno wiesz co robisz?
    _message raczej powinno być tylko jedno w obu klasach. Dziedziczenie
    polega na tym, że od przodka wjeżdża wszystko.
    Inny problem jest taki, że _message jest prywatna. W C++ oznacza to, że
    nie jest ona dostępna dla potomków. W takiej sytuacji gdy ma być ona
    dostępna również dla potomka sugerowałbym dyrektywę protected jeśli coś
    takiego w ogóle jest w tym języku (protected stosuję w C++).


  • 3. Data: 2019-09-05 09:50:15
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Roman Tyczka <n...@b...no>

    On Wed, 4 Sep 2019 22:11:10 +0200, Marek S wrote:
    > abstract class Test {
    > private _message: string;
    >
    > protected printMessage() {
    > console.log(this._message);
    > }
    >
    > protected constructor(message: string) {
    > this._message = message;
    >
    > }
    > }
    >
    > export default Test;
    >
    > *****************************************
    >
    > import Test from "./Test";
    >
    > class Test2 extends Test{
    > private _message: string;
    >
    > constructor(message:string) {
    > super("dupa");
    > this._message = message;
    > }
    >
    > execute() {
    > console.log(this._message);
    > this.printMessage();
    > }
    > }
    >
    > let demo = new Test2("my message");
    > demo.execute();
    >
    > Zadeklarowałem _message jako zmienną prywatną w obu klasach i... powstał
    > konflikt! Transkompilator nie poradził sobie z tym. Oczekiwałbym
    > samoczynnej zmiany nazwy funkcji by w wyjściowym JS nie było konfliktów.
    > Zatem jak żyć? :-) To samo dotyczy metod. Te prywatne zwalczają się
    > zamiast być niezależnymi w każdej z klas.

    Nie żabym się znał na TS, choć mam w planie nim się zająć, ale tak na
    logikę to zastanawia mnie które _message wg Ciebie miałaby wziąć metoda
    printMessage() wywołana z klasy Test2? Dla mnie to ewidentny konflikt.


    --
    pozdrawiam
    Roman Tyczka


  • 4. Data: 2019-09-05 19:43:52
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    W dniu 2019-09-05 o 09:50, Roman Tyczka pisze:
    >
    > Nie żabym się znał na TS, choć mam w planie nim się zająć, ale tak na
    > logikę to zastanawia mnie które _message wg Ciebie miałaby wziąć metoda
    > printMessage() wywołana z klasy Test2? Dla mnie to ewidentny konflikt.
    >

    Kurcze, jesteś drugą osobą, która o to dziś mnie pyta. Dla mnie sprawa
    jest tak oczywista jak oddychanie. Napisz sobie skrypt w PHP o podobnej
    strukturze i tam dostaniesz odpowiedź. Jeśli nie PHP, to może C#. Jeśli
    miałbym tworzyć standardy, to z pewnością powieliłbym zachowanie się
    prywatnych zmiennych z tego typu języków.

    Reasumując, metoda printMessage() powinno zwrócić wartość "dupa".
    Istnienie identycznej zmiennej prywatnej w klasie potomnej nie ma prawa
    nadpisywać tego, co jest w bazowej.

    Przedstaw mi swój tok rozumowania, który powoduje, że masz wątpliwości.
    Ciekawi mnie ich źródło.

    --
    Pozdrawiam,
    Marek


  • 5. Data: 2019-09-05 19:58:32
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    W dniu 2019-09-05 o 05:54, Szyk Cech pisze:

    > Na pewno wiesz co robisz?

    Wydaje mi się, że tak. Od lat programuję w natywnym JS.

    > _message raczej powinno być tylko jedno w obu klasach. Dziedziczenie
    > polega na tym, że od przodka wjeżdża wszystko.
    > Inny problem jest taki, że _message jest prywatna.

    No i o tym problemie mowa. W natywnym JS ES6 nie mam problemu z
    tworzeniem zmiennych prywatnych, a i metod też - choć ponoć takowe nie
    istnieją. TS już tego nie potrafi więc w tym zakresie kuleje. Oto przykład:

    Moduł 1:

    let privateMethod = Symbol();
    let privateVar = Symbol();

    class a {
    constructor() {
    this[privateVar]=5;
    }

    this[privateMethod]() {
    console.log(this[privateVar]);
    }

    printA() {
    this[privateMethod]();
    }

    }

    Moduł 2:

    import a from ...

    let privateMethod = Symbol();
    let privateVar = Symbol();

    class b extends a {
    constructor() {
    this[privateVar]=10;
    }

    printB() {
    this.printA();
    console.log(this[privateVar]);
    }

    }

    let obj = new b();
    obj.printB(); // metoda publiczna

    // 5
    // 10

    obj.printA(); //metoda publiczna

    //5

    obj[privateMethod](); //metoda prywatna

    //error

    W powyższym przykładzie privateVar jest prawdziwie prywatne dla obu
    klas. Wywołanie prywatnej metody privateMethod kończy się błędem. Da się
    to zrobić w ES6? Da się! A TypeScript wymięka. A wystarczyłoby aby
    transkodował prywatne zmienne i metody do konstrukcji z wykorzystaniem
    symboli.

    Kod pisałem z palca - więc mogłem jakieś błędy popełnić.

    --
    Pozdrawiam,
    Marek


  • 6. Data: 2019-09-05 20:21:27
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    Korekta. Już zauważyłem błąd. Zamiast:

    >   this[privateMethod]() {
    >     console.log(this[privateVar]);
    >   }

    Miało być:

    [privateMethod]() {
    console.log(this[privateVar]);
    }

    Jeśli jeszcze jakiś błąd będzie, to z góry przepraszam.

    --
    Pozdrawiam,
    Marek


  • 7. Data: 2019-09-06 13:55:47
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Tomek <s...@w...xx.pl>

    W dniu 05.09.2019 o 19:43, Marek S pisze:
    > W dniu 2019-09-05 o 09:50, Roman Tyczka pisze:
    >>
    >> Nie żabym się znał na TS
    >
    > Przedstaw mi swój tok rozumowania, który powoduje, że masz wątpliwości.
    > Ciekawi mnie ich źródło.
    >

    Też pojęcia nie mam o TS ale w JS jeśli wewnątrz funkcji jest
    wykorzystywane "this" to te "this" może znaczyć coś kompletnie innego w
    zależności od kontekstu jak jest wywoływana ta funkcja.


  • 8. Data: 2019-09-06 14:57:17
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    W dniu 2019-09-06 o 13:55, Tomek pisze:

    > Też pojęcia nie mam o TS ale w JS jeśli wewnątrz funkcji jest
    > wykorzystywane "this" to te "this" może znaczyć coś kompletnie innego w
    > zależności od kontekstu jak jest wywoływana ta funkcja.
    >

    Ok, ale ja nie o tym. Po pierwsze ustalmy, że nie chodzi o funkcje ale o
    klasy (słowo kluczowe class). Słowo kluczowe this w każdej metodzie
    klasy znaczy dokładnie to samo i ma zasięg całej klasy.

    A tematem rozmowy jest to, że w natywnym JS da się, choć nie pięknie,
    zdefiniować prywatne metody i właściwości. Natomiast w TS, prywatne
    zmienne są wpół prywatne. Transkompilator, podczas zamiany TS w JS, nie
    radzi sobie z przekształceniem prywatnych elementów do postaci JS, w
    taki sposób, by prywatność zachować. Zamiast tego wyświetla error
    mówiący o tym, że zmienna prywatna w klasie potomnej pokrywa się ze
    zmienną prywatną w klasie bazowej - co spowoduje konflikt. I faktycznie
    wynikowy kod JS nie będzie działał w takim przypadku.

    Konkluzja jest taka, że TS jest przydatny, ale wobec takiej niedoróby,
    póki co trzymam się natywnego JS. Jakoś mi się to wydaje
    nieprawdopodobne aby twórcy TS to przeoczyli. Dlatego podpytuję tutaj o
    to czy jest jakieś obejście problemu.

    --
    Pozdrawiam,
    Marek


  • 9. Data: 2019-09-07 16:12:42
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Roman Tyczka <n...@b...no>

    On Thu, 5 Sep 2019 19:43:52 +0200, Marek S wrote:

    >> Nie żabym się znał na TS, choć mam w planie nim się zająć, ale tak na
    >> logikę to zastanawia mnie które _message wg Ciebie miałaby wziąć metoda
    >> printMessage() wywołana z klasy Test2? Dla mnie to ewidentny konflikt.
    >>
    >
    > Kurcze, jesteś drugą osobą, która o to dziś mnie pyta. Dla mnie sprawa
    > jest tak oczywista jak oddychanie. Napisz sobie skrypt w PHP o podobnej
    > strukturze i tam dostaniesz odpowiedź.

    Ja nie napisałem, że nie znam odpowiedzi w innych językach, napisałem, że
    dla mnie to nie jest oczywiste jak Ci się wydaje.

    > Jeśli nie PHP, to może C#. Jeśli
    > miałbym tworzyć standardy, to z pewnością powieliłbym zachowanie się
    > prywatnych zmiennych z tego typu języków.

    To, że w jakichś językach jest to tak czy inaczej nie jest dowodem, że tak
    powinno być.

    > Reasumując, metoda printMessage() powinno zwrócić wartość "dupa".
    > Istnienie identycznej zmiennej prywatnej w klasie potomnej nie ma prawa
    > nadpisywać tego, co jest w bazowej.
    >
    > Przedstaw mi swój tok rozumowania, który powoduje, że masz wątpliwości.
    > Ciekawi mnie ich źródło.

    Źródłem są przemyślenia. Oto mój tok rozumowania:
    Tworzysz obiekt klasy Test2. Klasa Test2 ma prywatne pole ukryte pod
    this._message. Wołasz z tego obiektu metodę, która zwraca this._message.
    Skoro jest to obiekt klasy Test2 to dla tego typu this._message jest czymś
    innym niż dla typy Test, prawda? Dla mnie to sprawa oczywista jak
    oddychanie ;-) Jest tu wyraźna niejednoznaczność i punkt sporny, który
    warto wywalić na twarz chociażby ostrzeżeniem.

    To, że Java czy C# zwraca bezrefleksyjnie (czy są jakieś ostrzeżenia
    kompilatora?) wcale nie jest fajne, bo łatwo o masę głupich błędów, które
    transpiler TS wyłapuje jak zeznałeś. Mnie to bardzo cieszy, bo nie uważam,
    że taka praktyka jak identyczna nazwa prywatnego pola w dziedziczeniu to
    dobra praktyka. Ot wszystko.


    --
    pozdrawiam
    Roman Tyczka


  • 10. Data: 2019-09-08 00:07:37
    Temat: Re: TypeScript - jak uzyskać zmienne prywatne? Gdzie korzyści z TS?
    Od: Marek S <p...@s...com>

    W dniu 2019-09-07 o 16:12, Roman Tyczka pisze:

    >
    >> Jeśli nie PHP, to może C#. Jeśli miałbym tworzyć standardy, to z
    >> pewnością powieliłbym zachowanie się prywatnych zmiennych z tego
    >> typu języków.
    >
    > To, że w jakichś językach jest to tak czy inaczej nie jest dowodem,
    > że tak powinno być.

    Chwila, ale nie rozmawiamy tu o postępowaniu sądowym, czy rozkminianiu
    zagadek matematycznych by o jakichś dowodach wspominać.

    Jeśli chcesz bawić się w dowody zachowania się zmiennych prywatnych w
    JS, to z natury rzeczy stoisz na przegranej pozycji, bo czegoś takiego w
    JS nie ma ... przynajmniej do momentu gdy zastosujemy sztuczek, jakie
    opisałem. Wtedy można je wykrzesać nawet w natywnym JS i zachowują się
    one dokładnie tak samo jak w innych językach.

    Jeśli natomiast mówimy o zachowaniu się zmiennych prywatnych w TS to
    może warto wrócić do podstaw i przeczytać definicję zmiennej prywatne.
    Jej definicja jest jedna i wspólna dla wszystkich języków:

    https://pl.wikipedia.org/wiki/Zmienna_prywatna

    lub tu:

    https://pl.wikipedia.org/wiki/Zmienna_(informatyka)

    "Zmienne zadeklarowane w module mogą być zmiennymi prywatnymi modułu -
    dostępnymi wyłącznie z jego wnętrza - lub zmiennymi publicznymi
    (eksportowanymi) - dostępnymi tam, gdzie moduł jest wykorzystywany.
    Podobnie jest ze zmiennymi w klasie - mogą być dostępne:
    tylko dla danej klasy (zmienna prywatna),"

    https://www.p-programowanie.pl/cpp/klasy-c/

    "private - dostęp do składników klasy jest zabroniony z poza ciała klasy"

    Nie chcę już cytować linków na ten sam temat w kontekście PHP czy Java.
    Sposób zachowania zmiennych prywatnych jest tam również zgodny z definicją.

    TS łamie tą definicję. Zdefiniowana przez niego zmienna prywatna w
    klasie, w kodzie wynikowym będzie podlegać nadpisywaniu przez klasę
    potomną. Owszem, powstanie podczas transkompilacji absurdalny błąd,
    który nie ma prawa zaistnieć, a wadliwy kod wynikowy i tak wygeneruje się.

    > Źródłem są przemyślenia. Oto mój tok rozumowania: Tworzysz obiekt
    > klasy Test2. Klasa Test2 ma prywatne pole ukryte pod this._message.
    > Wołasz z tego obiektu metodę, która zwraca this._message. Skoro jest
    > to obiekt klasy Test2 to dla tego typu this._message jest czymś innym
    > niż dla typy Test, prawda? Dla mnie to sprawa oczywista jak
    > oddychanie ;-) Jest tu wyraźna niejednoznaczność i punkt sporny,
    > który warto wywalić na twarz chociażby ostrzeżeniem.
    >
    > To, że Java czy C# zwraca bezrefleksyjnie (czy są jakieś ostrzeżenia
    > kompilatora?) wcale nie jest fajne, bo łatwo o masę głupich błędów,
    > które transpiler TS wyłapuje jak zeznałeś. Mnie to bardzo cieszy, bo
    > nie uważam, że taka praktyka jak identyczna nazwa prywatnego pola w
    > dziedziczeniu to dobra praktyka. Ot wszystko.
    >

    Hmmm... wydaje mi się, że taki sposób rozumowania i obawy o to, co jak
    mają się zachowywać zmienne prywatne (niezależnie od języka
    programowania) wynikają z Twojego niezrozumienia czym w ogóle są zmienne
    prywatne. Zapewniam Cię, że ani w C ani w PHP obecność zmiennej
    prywatnej w klasie bazowej nie będzie podlegać nadpisaniu w klasie
    potomnej bo to są dwa oddzielne byty w dwóch różnych obszarach RAM.
    Żadne ostrzeżenia o używaniu zmiennych prywatnych w obu klasach nie
    powstaną w trakcie kompilacji C lub używania PHP bo ... nie ma o czym
    ostrzegać. Nie ma w tym żadnego błędu jak i obie zmienne nie będą w
    konflikcie. Jedynie TS się wyłamuje i nadużywa terminu prywatności.
    Przypuszczam, że jest to zwyczajny błąd twórców TS.

    Spytam jeszcze: czy Ty w ogóle programujesz z użyciem OOP? Masz
    wątpliwości co do najbardziej podstawowych pojęć w tej technice.

    --
    Pozdrawiam,
    Marek

strony : [ 1 ]



Szukaj w grupach

Szukaj w grupach

Eksperci egospodarka.pl

1 1 1

Wpisz nazwę miasta, dla którego chcesz znaleźć jednostkę ZUS.

Wzory dokumentów

Bezpłatne wzory dokumentów i formularzy.
Wyszukaj i pobierz za darmo: