2016-04-05 32 views
1

我執行研究目的的堆棧算法在科特林科特林:java.lang.UnsupportedOperationException在MutableList添加元素

class Stack<T:Comparable<T>>(list:MutableList<T>) { 

    var items: MutableList<T> = list 


    fun isEmpty():Boolean = this.items.isEmpty() 

    fun count():Int = this.items.count() 

    fun push(element:T) { 
     val position = this.count() 
     this.items.add(position, element) 
    } 

    override fun toString() = this.items.toString() 

    fun pop():T? { 
     if (this.isEmpty()) { 
      return null 
     } else { 
      val item = this.items.count() - 1 
      return this.items.removeAt(item) 
     } 
    } 

    fun peek():T? { 
     if (isEmpty()) { 
      return null 
     } else { 
      return this.items[this.items.count() - 1] 
     } 
    } 

} 

我試圖用這個代碼來執行:

fun main(args: Array<String>) { 

     var initialValue = listOf<Int>(10) as MutableList<Int> 
     var stack = Stack<Int>(initialValue) 
      stack.push(22) 
     println(stack.count()) 
     println(stack.isEmpty()) 
     println(stack.pop()) 
     println(stack.count()) 
     println(stack.isEmpty()) 

    } 

當我運行代碼時,我收到此錯誤:

Exception in thread "main" java.lang.UnsupportedOperationException 
at java.util.AbstractList.add(AbstractList.java:148) 
at Stack.push(Stack.kt:17) 
at StackKt.main(Stack.kt:45) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 
at java.lang.reflect.Method.invoke(Method.java:498) 
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:144) 

這與實施的跟隨行有關特德在推(元素:T)方法:

this.items.add(position, element) 

最奇怪的是,我用了一個非常相似的代碼實現orderedArray和它完美的作品。

你知道我在做什麼錯嗎?

回答

5

listOf<Int>不是真正可變的。據the doc

fun <T> listOf(vararg elements: T): List<T> (source) Returns a new read-only list of given elements. The returned list is serializable (JVM).

您應該使用mutableListOf<>代替。

爲什麼​​這裏允許的原因是因爲listOf(10)回報Collections.singletonList(10)它返回一個java.util.List(其中科特林假設實現kotlin.collections.MutableList接口)。所以編譯器在運行時調用mutating方法並拋出異常之前並不知道它是否真的不可變。

+1

所以解決的辦法是,在主要的方法,設置初始值與mutableListOf而不是listOf,對吧? – Sebastian

+0

是的。我更新了答案。 – szym

+1

爲什麼演員合法的解釋如下:'List'是一個接口,'MutableList'是一個擴展'List'的接口。因此,從'List'轉換爲'MutableList'是合法的,但它可以在運行時崩潰。 –