我需要获得一些与另一个匹配的字符串。例如,当我的字符串是"Ne"时,我需要获得"Neon"。我做了这个,但我认为这不是最好的方法。我认为最好使用密封类。有没有办法将字符串与密封类中的元素进行匹配?
fun getName(symbol: String): String{
return when(symbol){
"Ne" -> {"Neon"}
"Ar" -> {"Argon"}
"Kr" -> {"Krypton"}
"Xe" -> {"Xenon"}
"Rn" -> {"Radon"}
"Br" -> {"Bromine"}
else -> {""}
}
}
谢谢!
密封类可能对您没有太大帮助,但Enum可以,尤其是如果您以后想要做的不仅仅是获取全名(例如,获取原子量、本地化字符串资源ID或其他什么(。它还为您提供了一个强类型,因此您可以定义一个采用Element
枚举而不仅仅是字符串的函数。
enum class Element(val full_name: String, val num: Int) {
Ne("Neon", 10),
W( "Tungsten",74),
Fe("Iron", 26),
MISSING("", -1);
companion object {
// or just use Element.valueOf(), but this lets you make
// a MISSING entry to return instead if you want
fun fromSymbol(sym: String): Element {
return try {
valueOf(sym)
} catch(e: IllegalArgumentException) {
MISSING;
}
}
fun fromNumber(n: Int): Element {
return values().firstOrNull { it.num == n } ?: MISSING
}
}
}
这比when
方法更具可扩展性,因为您可以在保持单个查找的同时向元素添加额外的属性。它的作用就像一个密封类(有点(,因为您不能添加任何未在枚举中定义的元素。
添加到枚举中的任何属性都可以使用,如原子序数、重量、全名或任何其他要添加的属性。
val e = Element.valueOf("Ne")
println("Element is ${e.full_name} - number ${e.num}")
// or
val e = Element.fromSymbol("Ne")
println("Element is ${e.full_name} - number ${e.num}")
// or
val e = Element.fromNumber(10)
println("Element is ${e.full_name} - number ${e.num}")
使用伴随对象getter而不是Element.valueOf
也可以让您做一些事情,比如使检索不区分大小写
fun fromSymbol(sym: String): Element {
return values().firstOrNull { it.name.lowercase() == sym.lowercase() } ?: MISSING
}
本地化
如果您想本地化元素名称,枚举方法在将来也可以很容易地进行调整。您可以将本地化的名称放在strings.xml文件中,并在枚举中设置资源ID,而不是原始字符串
enum class Element( val name_id: Int, val num: Int) {
Ne(R.string.neon,10),
Fe(R.string.iron,26);
fun getName(ctx: Context): String {
return ctx.getString(name_id)
}
companion object {
//...
}
}
val e = Element.fromSymbol("Ne")
println("Name is ${e.getName(ctx)}")
密封类并不能真正帮助您(不过您可能还有其他原因(。您仍然需要一些方法将短名称转换为长名称。有两种方法:
1( 使用一个包含短名称和长名称的类。遍历该列表,直到找到匹配项。这是一个O(n(运算。
2( 保留简短名称的映射->长名称(或短名称->具有长名称的类(。然后你只需要做一个地图查找。这是一个O(1(运算。
你想要的是第二个。如果这给你带来了其他优势,你仍然可以在那里使用一个密封的类,但你想要快速查找的映射。
Sealed class
不是更好的方法,因为您可能必须在密封类中为每个元素创建一个类。如果你有很多课程,不建议这样做。同样的事情也适用于enums
。你的情况什么时候好。
或者,您可以将其作为键值对存储在hashmap中。并按键获取元素。
var elements = hashMapOf(
"Ne" to "Neon",
"Ar" to "Argon",
"Kr" to "Krypton",
"Xe" to "Xenon",
"Rn" to "Radon",
"Br" to "Bromine"
)
val item = elements["as"]?:""
若映射中不存在元素,?:
运算符(elvis(将给出空字符串。