2016-01-25 3 views
0

Объяснение: Я принял gzm0's ответ, потому что он качался!Scala error "value map не является членом Double"

@Eduardo пришел к выводу, что: (for(i <- 10..20; j=runTest(i)) yield i -> j).toMap, который также позволяет мне запускать сборку, он просто не отправил ответ, а ответ @ gzm0 был концептуально УДИВИТЕЛЬНЫМ, поэтому я принял его.

Once I get this other issue figured out relating to "can't call constructor" я буду в состоянии проверить эти вне на самом деле работает программа LOL

Вопрос: У меня есть ошибка в этом выражении, в частности, как это исправить, но в более общем смысле, что я пропускаю о FP или Scala для сделать эту ошибку?

timingsMap = for (i <- powersList; j <- runTest(i)) yield i -> j 

Я пишу свой первый проект Gradle/Scala для анализа назначения алгоритмов. Scala не является частью задания, поэтому я не использую тег домашней работы. За исключением моей работы с Spark на Java, я совершенно новый для функционального программирования. Я уверен, что это проблема.

Вот отрывок, the full .scala file is on GitHub, это нормально, или я буду размещать полную программу здесь, если я крутился :)

val powersList = List(10 to 20) 

    // create a map to keep track of power of two and resulting timings 
    var timingsMap: Map[Integer, Double] = Map() 

    // call the runTest function once for each power of two we want, from powersList, 
    // assign timingsMap the power of 2 value and results of runTest for that tree size 
timingsMap = for (i <- powersList; j <- runTest(i)) yield i -> j 

Ошибка:

/home/jim/workspace/Scala/RedBlackTree4150/src/main/scala/Main.scala:36: value map is not a member of Double 
    timingsMap = for (i <- powersList; j <- runTest(i)) yield i -> j 

Что я думаю Я делаю так, что строка timingsMap = ... получает все элементы powersList, отображаемые на i для каждой итерации цикла, а возвращаемое значение для runTest(i), отображаемое на j для каждой итерации, а затем взяв все эти пары и помещая их в timingsMap. Я пытаюсь использовать i в цикле до call runTest(i), что вызывает проблему?

RunTest выглядит следующим образом:

def runTest(powerOfTwo: Range): Double = { 

    // create the tree here 
    var tree = new TreeMap[Int, Double] 

    // we only care to create a tree with integer keys, not what the value is 
    for (x <- powerOfTwo) { 
     // set next entry in map to key, random number 
     tree += (x -> math.random) 
    } 

    stopWatchInst.start() 

    // now go through and look up all the values in the tree, 
    for (x <- powerOfTwo) { 
     // get the value, don't take the time/overhead to store it in a var, as we don't need it 
     tree.get(x) 
    } 

    // stop watch check time report and return time 
    stopWatchInst.stop() 
    val totalTime = stopWatchInst.elapsed(TimeUnit.MILLISECONDS) 
    loggerInst.info("run for 2 to the power of " + powerOfTwo + " took " + totalTime + " ms") 
    return totalTime 
    } 

Примечание: У меня было предложения, чтобы изменить j <- к = в j <- в этой строке: timingsMap = для (I < - powersList; J < - runTest (i)) выход i -> j

Другое предложение вообще не нравилось использовать выход и предлагалось заменить (от 10 до 20). ...

Странная часть существующего кода не отображает ошибку в редакторе IntelliJ, только разрывается при запуске. Все предложения дают ошибки несоответствия типов в среде IDE. Я действительно пытаюсь выяснить концептуально, что я делаю неправильно, спасибо за любую помощь! (И, конечно, мне нужно, чтобы заставить его работать!)


После попытки gzm0 ответа я получаю вниз по той же дороге ... мой код, представленные не показывают какие-либо несоответствия типов, пока я не использовать gradle run. .. тогда, когда я делаю предложенные изменения, он начинает давать мне ошибки прямо в среде IDE ... но продолжайте их!Вот последняя ошибка на основе gzm0s ответа:

/home/jim/workspace/Scala/RedBlackTree4150/src/main/scala/Main.scala:37: type mismatch; 
found : List[(scala.collection.immutable.Range.Inclusive, Double)] 
required: Map[Integer,Double] 
    timingsMap = for (i <- powersList) yield i -> runTest(i) 
+1

Взял parens из класса 'RedBlackTree4150()' не имело никакого значения, я вижу ... У меня есть доступ через Safari Books к Learning Scala и Wampler's Programming Scala, поэтому, если есть хорошая ссылка, пожалуйста, используйте главы/разделы заголовков, а не номера страниц спасибо :) – JimLohse

+0

Был ответ, но он превратился в длинную дискуссию, и он не хотел идти в чат, я хочу, чтобы этот пользователь не удалил ответ! Они предполагали, что я использую что-то вроде (от 10 до 20) .map, но мы попали во множество несоответствий типов. Я думаю, что то, что я делаю с 'for ... yield', совпадает с картой под капотом. Есть ли причина избежать «для ... урожая»? Этому пользователю это не понравилось. – JimLohse

+1

используйте 'j = runTest (i)' с '=', а не '<-'. Знак '<-' предназначен для тех случаев, когда у вас есть коллекции. 'runTest' просто возвращает значение« Double » – Eduardo

ответ

3

Вы хотите:

for (i <- powersList) 
    yield i -> runTest(i) 

Результат runTest не список, поэтому вы не можете дать его for заявление. Причина, по которой вы получаете немного сообщения странной ошибки, из-за того, как ваш for является обессахаренным:

for (i <- powersList; j <- runTest(i)) yield i -> j 

// turns into 

powersList.flatMap { i => runTest(i).map { j => i -> j } } 

Однако результат runTest(i) является Double, который не имеет методы map. Поэтому, глядя на обесцвечивание, сообщение об ошибке действительно имеет смысл.

Обратите внимание, что моя точка о результате runTest «s не является списком не совсем правильно: Все, что есть метод map, который позволит вышеуказанному заявлению (то есть, принимая какое-то лямбда) будет делать. Однако это выходит за рамки этого ответа.

Теперь мы успешно создали список кортежей (с powersList является List, результатом цикла for является List, а). Однако мы хотим получить Map. К счастью, вы можете позвонить по toMapList S, которые содержат кортежи, чтобы преобразовать их в Map:

val tups = for (i <- powersList) yield i -> runTest(i) 
timingsMap = tups.toMap 

примечания в стороне: Если вы действительно хотите сохранить j внутри for -loop, вы можете использовать знак равенства вместо левой стрелки:

for (i <- powersList; j = runTest(i)) yield i -> j 

Это превратится в:

powersList.map { i => 
    val j = runTest(i) 
    i -> j 
} 

Это то, что вы хотите.

+0

Я положил' timingsMap = for (i <- powersList) результат i -> runTest (i) 'и получите эту ошибку:' /home/jim/workspace/Scala/RedBlackTree4150/src/main/scala/Main.scala:37: тип несоответствия; найдено: Список [(scala.collection.immutable.Range.Inclusive, Double)] required: Map [Integer, Double] timingsMap = for (i <- powersList) yield i -> runTest (i) ', который я буду редактируйте в мой вопрос для удобочитаемости – JimLohse

+0

@ChrisMartin Я знаю. Добавлено больше объяснений. Это все еще недостаточно ясно, я улучшусь. – gzm0

+0

Позвольте мне прочитать ваш пересмотренный ответ, я добавил ошибку до конца моего ответа ... действительно оцениваю предложения каждого, но они запускают меня по пути несоответствий типа ..., это нормально, если оно ведет где-то :) ... AHHHH просто прочитал ваш расширенный ответ. ОЧЕНЬ ХОЛОДНЫЕ СПАСИБО, позвольте мне попробовать, это объяснение, которого я ждал! – JimLohse

Смежные вопросы