【问题标题】:Kotlin enum type where child is interchangeable with parentKotlin 枚举类型,其中子级可与父级互换
【发布时间】:2020-11-17 19:00:29
【问题描述】:

我有一个类Transaction,其子类IncomeExpense 有一个属性category。收入和支出有不同的类别,即IncomeCategoryExpenseCategory。我需要一份收入和支出的清单,所以我创建了一个交易清单。但我还需要访问他们的类别,所以Transaction 也需要一个类别属性。由于类别可以采用的值是有限的,因此枚举或密封类将非常实用。但我需要一些超类型与子类型可互换的东西。

有没有办法指定一个通用类别,以便 Transaction 类可以接受IncomeCategoryExpenseCategory 作为参数?

P.S.:抱歉标题太糟糕了,我想不出更好的方式来描述我的问题

【问题讨论】:

  • 您可以让incomecategory 和expensecategory 扩展一个共享类型的类别
  • @dazza5000 如何用常规类(如枚举)表示一组有限的值
  • 貌似@TenFour04有货了:)
  • Transaction每一种 类型都有类别吗?

标签: kotlin inheritance enums sealed-class


【解决方案1】:

如果 Category 需要是一个密封的类(例如,IncomeCategory 和 ExpenseCategory 的实例需要携带状态),你会这样做。顶级 Transaction 类使用泛型类型来表示其类别,因此如果您想要两种 Transactions 类型的列表,您可以声明List<Transaction<Category>>

sealed class Category
class IncomeCategory: Category()
class ExpenseCategory: Category()

abstract class Transaction<out T: Category>(val category: T)

class Income(category: IncomeCategory): Transaction<IncomeCategory>(category)
class Expense(category: ExpenseCategory): Transaction<ExpenseCategory>(category)

如果您需要能够更改类别实例,那么您不能在声明站点将类型 T 声明为协变 out,并且您必须在引用的地方声明它是协变的列表:List&lt;Transaction&lt;out Category&gt;&gt;。然后你可以使用var 而不是val 来代替category

如果Category 可以只是一个枚举,这更简单,因为您不需要泛型:

enum class Category {
    IncomeCategory,
    ExpenseCategory
}

abstract class Transaction(val category: Category)

class Income(): Transaction(Category.IncomeCategory)
class Expense(): Transaction(Category.ExpenseCategory)

【讨论】:

  • 是否还可以添加更多类别值?例如。当用户想要添加自定义类别时(抱歉,忘记在帖子中提及)。
  • 是的,如果“用户”是指图书馆的用户,并且如果您将类别抽象而不是密封。然后用户可以按照我的第一个示例中的模式创建新的类别和交易类型。
  • 如果是应用程序的用户?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-11-17
  • 1970-01-01
  • 1970-01-01
  • 2012-09-16
  • 2014-05-15
  • 2017-04-09
  • 1970-01-01
相关资源
最近更新 更多