我正在处理一个抽象类和两个具体的类,它们实现了抽象类。下图如下:
kotlin - 如何处理Kotlin中的多态性-LMLPHP

我的类(class)如下:

abstract class NavItem() {
    var attributes: String = ""
    var text = ""
}

class NavMenu(val items: MutableList<NavItem>) : NavItem()

class NavLink(var shortText: String) : NavItem()

问题是,当我尝试使用可能是NavMenu或NavLinks的项目时,NavMenus有一个NavLinks集合。

我正在尝试使用多态性作为下一个代码的项目:
navMenu.items.forEach{ item ->
            buildNavItem(item)
        }

buildNavItem方法似乎是:
private fun buildNavItem(navMenu: NavMenu){
        navMenu.items
        navMenu.attributes
        navMenu.items
    }

    private fun buildNavItem(navItem: NavItem){
        navItem.text
        navItem.attributes
    }

    private fun buildNavItem(navLink: NavLink){
        navLink.text
        navLink.attributes
    }

但是代码总是进入buildNavItem(navItem:NavItem)中,即使在每个代码中我有时都可以看到该项目是NavLink或NavMenu。

有什么建议吗?

谢谢!!

最佳答案

问题:

navMenu.items.forEach { item ->
    item.buildNavItem()
}

由于items的类型为List<NavMenu>,因此编译器将调用适合于item类型的NavMenu的函数,在这种情况下,重载需要NavMenu

解决方案:

为了调用更具体的重载,编译器需要知道类型。您可以智能投射项目,然后调用适当的函数:
private fun buildNavItem(navMenu: NavMenu) {
   when(navMenu){
      is NavItem -> buildNavItem(navMenu) // navMenu is smart casted to NavItem
      is NavLink -> buildNavItem(navMenu) // navMenu is smart casted to NavLink
      else -> throw IllegalStateException("Unknown subtype ${navMenu::class.simpleName} of NavMenu")
   }
}

这样,无论何时调用buildNavItem,都可以委托(delegate)给适当的函数。

关于kotlin - 如何处理Kotlin中的多态性,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/53951311/

10-12 04:02