Прежде всего, я должен сказать, что нет смысла использовать функцию предложения общего назначения без явного формата, потому что, как и комментарии @gidds и @DodgyCodeException, он подвержен неоднозначности.
Таким образом,Я решил использовать regex
для сопоставления разделителя десятичных точек, сгруппированных запятыми [0-9]+(,[0-9]{3})*\\.[0-9]{2}
, и инвертированного регистра [0-9]+(\\.[0-9]{3})*,[0-9]{2}
(разделителя запятых, сгруппированных по точкам).Затем очистите запятые и замените точки, чтобы получить десятичный формат без группировки точек, который я хочу проанализировать в Double
. Я делаю это так, как extension function
:
const val NOTHING = ""
const val COMMA = ","
const val POINT = "."
val commaGrouped = "[0-9]+(,[0-9]{3})*\\.[0-9]{2}".toRegex()
val pointGrouped = "[0-9]+(\\.[0-9]{3})*,[0-9]{2}".toRegex()
fun String.commaCleaned() = replace(COMMA, NOTHING)
fun String.pointCleaned() = replace(POINT, NOTHING)
fun String.commaToPoint() = replace(COMMA, POINT)
fun String.pointToComma() = replace(POINT, COMMA)
fun String.toDouble() =
when {
commaGrouped matches this -> Double(commaCleaned())
pointGrouped matches this -> Double(pointCleaned().commaToPoint())
else -> throw IllegalArgumentException(
"the value ${this} can't be converted to ${Double::class.java} " +
"have match ${commaGrouped.pattern} " +
"or ${pointGrouped.pattern}")
}
что целочисленный формат или десятичная точность больше двух не будет соответствовать для создания Double
, и это то, что я тоже хочу.