2013-02-28 18 views
5

DlaczegoScala za wykonanie zrozumieniem

for (
    a <- 1 to 1000; 
    b <- 1 to 1000 - a; 
    c <- 1 to 1000 - a - b; 
    if (a * a + b * b == c * c && a + b + c == 1000) 
) println((a, b, c, a * b * c)) 

266 ms

wolniej następnie:

for (a <- 1 to 1000) 
    for (b <- 1 to 1000 - a) 
    for (c <- 1 to 1000 - a - b) 
     if (a * a + b * b == c * c) 
     if (a + b + c == 1000) 
      println((a, b, c, a * b * c)) 

62 ms

Jeśli rozumiem rozwiązać ten powinien być taki sam?


Rozwiązanie po odpowiedziach przetwarzania:

for (
    a <- 1 to 1000; 
    b <- 1 to (1000 - a) 
) { 
    val c = (1000 - a - b) 
    if (a * a + b * b == c * c) 
    println((a, b, c, a * b * c)) 
} 

9 ms

+0

Naprawdę przydatne jest napisanie przynajmniej wersji Scala, której używałeś. Co najwyżej system operacyjny i inne powiązane informacje. –

+0

Używam Windows 7 i wersji 2.9.2 używając eclipse z jre7. – Jeff

+3

Dziwny sposób na poszukiwanie rozwiązań - potrzebujesz 'a + b + c == 1000', więc dlaczego nie ustawić po prostu' c = 1000 - a - b'? (Oczywiście nie jest to odpowiedź na pytanie ...) –

Odpowiedz

13

Twoje rozumienie jest błędne.

for(x <- coll) if(condition) dosomething 

przełoży się

coll.foreach{x => if(condition) dosomething } 

for(x <- coll if(condition)) dosomething 

co przełoży się

coll.withFilter(x => condition).foreach{ x => dosomething } 

Możesz zajrzeć na The Scala Language Specification 6.16 więcej szczegółów.

9

Możesz sprawdzić this presentation (slides 13-15), aby dowiedzieć się, jak pętle są tłumaczone wewnętrznie.

Główną różnicą Do przykładów należą:

  • stan, w pętli do ciała (2), np
  • stanu w generatorze (przykład 1)

ostatnie , zwany także do filtrowania pętlowego ma wadę wydajnościową według projektu. Aby maksymalnie uprościć to, co się dzieje: W ramach withFilter (który jest pierwszym krokiem tłumaczenia) tworzona jest anonimowa nowa funkcja typu Function2[Object, Boolean] (która służy do oceny warunku). Parametr przekazywany do jego funkcji apply musi być w ramce, ponieważ jest zdefiniowany na podstawie Object. To boksowanie/rozpakowywanie jest znacznie wolniejsze od oceny stanu if bezpośrednio w ciele pętli for, co pozwala na bezpośredni dostęp do zmiennych.

+0

Te slajdy są bardzo ciekawe, a nawet znalazły lepsze rozwiązanie :) – Jeff

+0

@Dvvoter: Czy mógłbyś wyjaśnić, co jest nie tak z moją odpowiedzią? – bluenote10

Powiązane problemy