2014-10-03 18 views
7

Ostatnio dużo programowałem w Swift. Dzisiaj zrobiłem trochę pracy w JavaScipt, gdy pojawiło się pytanie:Opcjonalne łańcuchy w JavaScript

Czy jest coś podobnego do opcjonalnego łańcucha w JavaScript? Sposób na zapobieżenie undefined is not an object bez żadnych zmiennych?

przykład:

function test(){ 
    if(new Date() % 2){ 
     return {value: function(){/*code*/}}; 
    } 
} 

test().value(); 

zawiedzie połowie czasu, ponieważ czasami test powraca nieograniczony.

Jedynym rozwiązaniem można myślę, jest funkcją:

function oc(object, key){ 
    if(object){ 
     return object[key](); 
    } 
} 

oc(test(), 'value'); 

Chciałbym móc zrobić coś takiego:

test()?.value() 

Część po znaku zapytania jest wykonywana tylko wtedy, gdy test zwrócił obiekt.

Ale to nie jest bardzo eleganckie. Czy jest coś lepszego? Magiczna kombinacja operatorów?

Edytuj Wiem, że mogę przepisać test, aby zwrócić coś. Ale zastanawiam się, czy istnieje coś takiego jak opcjonalne połączenie. Nie interesuje mnie konkretne rozwiązanie powyższego przykładu :. Coś, co mogę również użyć, jeśli nie mam kontroli nad funkcją zwracającą niezdefiniowaną.

+0

co chcesz zwrócić wartość(), gdy test() zwraca niezdefiniowany? –

+0

@ ZaheerAhmed false lub undefined. To nie ma znaczenia. – idmean

+0

można zawinąć istniejącą funkcję, aby przywrócić domyślną wartość w przypadku niezdefiniowanej, bez przepisywania. możesz również użyć potrójnego (x? y: z)() lub domyślnego operatora (x || y)() w czasie połączenia. – dandavis

Odpowiedz

5

W zwykłym kodzie JavaScript musisz sprawdzić typ lub strukturę swojego kodu, aby wiedzieć, że obiekt będzie istnieć.

CoffeeScript, język kompilujący się do JavaScript, zapewnia egzystencjalnego operatora ?. dla bezpiecznego łączenia, jeśli jesteś gotów rozważyć przetwarzany język.

Istnieje inna dyskusja here o tym, dlaczego nie można odtworzyć tego zachowania w JS.

Istnieje również dyskusja on the ESDiscuss forums o dodaniu operatora egzystencjalnego do przyszłej wersji JavaScript. Wydaje się jednak, że nie jest to zbyt daleko, a już na pewno nie zbliży się do praktycznego zastosowania. Więcej pomysłu w tym momencie.

+2

Zaakceptowałem twoją odpowiedź, ponieważ to naprawdę odpowiada na moje pytanie w przeciwieństwie do innych odpowiedzi poniżej i ponieważ dostarcza kilku interesujących informacji. – idmean

0

Co powiesz na zwracanie funkcji Noop, która nie robi nic, gdy warunek nie zostanie spełniony?

function test(){ 
    if(new Date() % 2){ 
     return {value: function(){/*code*/}}; 
    } 
    return {value: function(){ /* just return a type consistent with the function above */ } 
} 
+0

To był tylko przykład. Mówię o funkcjach, na które nie mam wpływu. – idmean

+0

gotcha. Przepraszam. Potrzebujesz czegoś takiego jak operator '? .' w Groovy. W JS nie ma czegoś takiego. – sebnukem

0

Zawsze można return this;, jeśli test jest metodą obiektową.

Ale dlaczego chcesz zapobiec takim błędom, tworząc fałszywe funkcje?

+0

OP zadawał ogólne pytanie o bezpieczne łańcuchy, a nie jak skonstruować określoną funkcję, aby była bezpieczna. –

3

Można użyć

test() && test().value(); 

lub

var testResult = test(); 
testResult && testResult.value(); 

Jeśli pytasz mnie to jest najbardziej podobny do Swifta opcjonalnym łańcuchowych.