• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Proszę o łopatologiczne wyjaśnienie dlaczego tak się dzieje.

Object Storage Arubacloud
0 głosów
271 wizyt
pytanie zadane 4 czerwca 2017 w JavaScript przez Konfeusz Bywalec (2,810 p.)
otagowane ponownie 4 czerwca 2017 przez Konfeusz

Witam.

Przerabiam książkę, "... JavaScript, rusz głową" i tam jest takie zadanie do rozwiązania:

var balance = 10500;
var cameraOn = true;

function steal(balance, amount){
    
    cameraOn = false;
    if (amount < balance){
        balance = balance - amount;
    }    
    return amount;
    cameraOn = true;    
}

var amount = steal(balance, 1250);
console.log(amount);
console.log(balance);
console.log(cameraOn);

 

Dlaczego zmienna balance nadal posiada wartość 10500 po wykonaniu skryptu? W rozwiązaniu jest napisane, że balance z parametru funkcji przesłania początkową zmienną globalną var balance. Ale jeśli wywołam na początku funkcji ...

function steal(balance, amount){
    console.log(balance);
...

to w konsoli balance ma poprawnie 10500. Dlaczego ta wartość nie jest pomniejszona o wartość 1250;

 

Jeśli pytanie wydaje się Wam infantylne, to proszę o wyrozumienie... dopiero się tego uczę.

komentarz 4 czerwca 2017 przez ScriptyChris Mędrzec (190,190 p.)

Drobna uwaga - jeśli w książce o tym nie wspominają:

    return amount;
    cameraOn = true;

Kod po linijce ze słówkiem return nie wykona się, więc zmienna cameraOn nie będzie miała po tym kodzie wartości true. Może się wydawać, że wyjątek stanowi tutaj deklaracja funkcji poniżej słówka return - no bo dlaczego taki kod miał by działać, gdyby po return już nic się w funkcji nie mogło wykonać?

function foo() {
   bar();
   return true;

   function bar() {
     console.log('Function statement hoisting.');
   }
}

foo();

// Function statement hoisting.
// true

Deklaracje funkcji za pomocą słówka function podlegają zjawiskowi hoisting. To tak na marginesie, jeśli w książce tego nie tłumaczą :)

A skąd pomysł, aby deklarować funkcje poniżej użycia słówka return? Choćby taki: https://github.com/johnpapa/angular-styleguide/blob/master/a1/README.md#accessible-members-up-top

komentarz 4 czerwca 2017 przez Konfeusz Bywalec (2,810 p.)
Tak, tak. Problem w tym, że to "zadanie z książki z haczykiem". Czyli należało wskazać dlaczego nie działa poprawnie. Ale po rozwiązaniu nie wyjaśnili do końca wszystkiego, stąd moje pytanie o pomoc na forum, bo nie do końca rozumiałem dlaczego tak a nie inaczej.

2 odpowiedzi

+1 głos
odpowiedź 4 czerwca 2017 przez Chess Szeryf (76,710 p.)
edycja 4 czerwca 2017 przez Chess

Zmienna balance jest w parametrze funkcji, dlatego konsola ci wypisuje:

1250
10500
false

console.log(amount);  // wywołuje funkcję, wypisuje, więc 1250, bo jest tam return amount;.

Zmienna balance odwołuje się do zmiennej globanej z początku skryptu, czyli wypisuje ci 10500.

console.log(cameraOn); // wyrzuca ci false, ponieważ funkcja steal została wcześniej wywołana, a w środku tej funkcji jest cameraOn = false; wartość ta przesłania tę: cameraOn = true;.

 

 

 

komentarz 4 czerwca 2017 przez Konfeusz Bywalec (2,810 p.)
To rozumiem, ale jak poprawić kod, by ostatecznie balance posiadało wartość 10500 - 1250 czyli 9250?
komentarz 4 czerwca 2017 przez amiluke Obywatel (1,120 p.)
a przypadkiem console.log(amount) nie wyświetla wartości samej zmiennej a funkcja wywołana jest przy zadeklarowaniu zmiennej amount i przypisaniu do niej wyniku funkcji steal? var amount = steal(balance, 1250); w tym miejscu
komentarz 4 czerwca 2017 przez Chess Szeryf (76,710 p.)
edycja 4 czerwca 2017 przez Chess

Usuń tę linię: return amount;

I daj (w tych nawiasach klamrowych): return balance = balance - amount;.

 

+1 głos
odpowiedź 4 czerwca 2017 przez amiluke Obywatel (1,120 p.)
Funkcja steal wykorzystuje wewnątrz siebie zmienną balance podaną w parametrze ale na końcu zwraca tylko wartość amount którą następnie przypisujesz do zmiennej globalnej amount. Reszta danych z wewnątrz funkcji steal zostaje utracona, innymi słowy owszem przesłania początkową zmienną balance ale tylko dla siebie, do własnego użytku. Natomiast kiedy wklejasz console.log(balance) do wewnątrz funkcji steal wyświetlasz chwilowy stan tej zmiennej kiedy funkcja zostaje wywołana. Dlatego kiedy wyświetlasz wartość zmiennej balance poza funkcją zostaje ona nie zmieniona.
komentarz 4 czerwca 2017 przez Konfeusz Bywalec (2,810 p.)
Ok, już chyba rozumiem, dzięki.

W całym, zadaniu był haczyk właśnie w tym, że wywołanie funkcji było przypisane do zmiennej var amount. Taka forma przekręciła cały sens przykładu. Czy dobrze kombinuje?
komentarz 4 czerwca 2017 przez Chess Szeryf (76,710 p.)
console.log(amount);  to to samo, co: console.log(steal(balance, 1250));
komentarz 4 czerwca 2017 przez Konfeusz Bywalec (2,810 p.)

No tak.

Poprawiłem to wszystko tak:

var balance = 10500;
var cameraOn = true;

function steal(balance, amount){
    cameraOn = false;
    if (amount < balance){
        return balance = balance - amount;
    }
    
    
    return balance;
}

    
var wynik = steal(balance, 1250);
balance = wynik;
var cameraOn = true;
console.log(balance);
console.log(cameraOn);

Dzięki za objaśnienie. Brakowało mi tego w przykładzie książki. Książka jest naprawdę fajna, ale ma pewne niedociągnięcia, ale dobrze że można liczyć na pomoc na forum.

Jeszcze raz wielkie dzięki.

komentarz 4 czerwca 2017 przez Chess Szeryf (76,710 p.)

Te samo return balance; wydaje mi się niepotrzebne. Jeśli warunek się niespełni

if (amount < balance) /* .... */ to wtedy return balance zwróci ci 10500, jeśli tego return'a nie będzie, a wywołasz funkcję to zwróci ci ona wartość undefined.

 

komentarz 4 czerwca 2017 przez Konfeusz Bywalec (2,810 p.)
tak, tak... racja, już poprawiłem. Dzięki.

Podobne pytania

0 głosów
2 odpowiedzi 200 wizyt
pytanie zadane 5 lutego 2020 w C i C++ przez ullortnaci Nowicjusz (220 p.)
0 głosów
1 odpowiedź 93 wizyt
pytanie zadane 25 marca 2018 w JavaScript przez Paweł123 Nałogowiec (33,500 p.)
0 głosów
2 odpowiedzi 274 wizyt
pytanie zadane 1 listopada 2016 w PHP przez toster234 Początkujący (370 p.)

92,579 zapytań

141,432 odpowiedzi

319,663 komentarzy

61,964 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj.

Akademia Sekuraka

Kolejna edycja największej imprezy hakerskiej w Polsce, czyli Mega Sekurak Hacking Party odbędzie się już 20 maja 2024r. Z tej okazji mamy dla Was kod: pasjamshp - jeżeli wpiszecie go w koszyku, to wówczas otrzymacie 40% zniżki na bilet w wersji standard!

Więcej informacji na temat imprezy znajdziecie tutaj. Dziękujemy ekipie Sekuraka za taką fajną zniżkę dla wszystkich Pasjonatów!

Akademia Sekuraka

Niedawno wystartował dodruk tej świetnej, rozchwytywanej książki (około 940 stron). Mamy dla Was kod: pasja (wpiszcie go w koszyku), dzięki któremu otrzymujemy 10% zniżki - dziękujemy zaprzyjaźnionej ekipie Sekuraka za taki bonus dla Pasjonatów! Książka to pierwszy tom z serii o ITsec, który łagodnie wprowadzi w świat bezpieczeństwa IT każdą osobę - warto, polecamy!

...