String "2" toInt returns 50 - kotlin

Im just working through some simple practice problems in kotlin. In my code below I'm taking a number and attempting to add the number members together. Ex. 29, return 2 + 9 = 11. There could be a better way to accomplish this but, I'm taking the numbers, converting to string, and then putting them into a list, ie ["2","9"] when I attempt to convert list[0].toInt() it returns 50. It appears there is some rounding taking place but I have not found another kotlin method to work with. Can anyone offer some insights? TIA
fun main(args: Array<String>) {
fun addTwoDigits(n: Int): Int {
val sliced = n.toString().toList()
val int1 = sliced[0].toInt()
println(sliced[0]) //returns "2"
println(int1) // returns 50
return sliced[0].toInt() + sliced[1].toInt()
}
println(addTwoDigits(29))
}

Koltin Char.toString(), which you are using in line:
val int1 = sliced[0].toInt()
converts the character using the ASCII Code table.
You can simply add a toString() call before the toInt() call:
val int1 = sliced[0].toString().toInt()

Related

Is it valid to use readLine()!! without adding toInt() if the input is an Int?

Sorry for this dumb question:
It says readLine()!! reads line as a string, but if I enter an integer without adding .toInt(), it runs fine?:
Sample input: 55
fun main() {
println("Enter any number here: ")
val a = readLine()!!
print(a)
}
//prints 55
I am a bit confused, because it prints 55 without any issues. So, readLine()!! can read any type of data and return 55, even if it's not a String?
Actually the 55 you entered is a string and it was printed as string representation also. You couldn't use the 55 to do arithmetic computation eg. 55 - 10 without make it as integer or other number representation like double.
You can check the type like this
if (a is String) {
print("It's string")
}

NumberFormat to Number in Kotlin

I really want to know how to make the inverse process of this
fun makeAFormattedString(currencyCode: String, numberToConvert: Float): String{
val format: NumberFormat = NumberFormat.getCurrencyInstance()
format.maximumFractionDigits = 2
format.currency = Currency.getInstance(currencyCode)
return format.format(numberToConvert)
}
when I type: ("MXN",3000) my result is
"MX $3000.00"
I want to know how to get the number (3000) with this string
"MX $3000.00"
"MX $3000.00".takeLastWhile { it != '$' }
is one of many ways.
val result = "[^\\d]+?(\\d+\\.?\\d*)".toRegex().find("MX $3000.00")
result?.groupValues?.last()
works too.
The problem is there's no way to tell whether you started with an Int or a Float. If you started with 3000, it formats as 3000.00 and if you started with 3000.45, it formats as 3000.45. The result will be a Float, and you can choose what to do with it.

Format a number to string, fill 0 when it's not enough two characters

I want to format the number to String and fill 0 when it's not enough two characters
fun formatDuration(val duration):String {
val minutes = duration.toInt() / 60
return "$minutes"
}
For example, if minutes is 6, it should displayed 06 rather than 6.
You can padStart the toString() result of minutes.
I tried your code in the Kotlin Playground and it wasn't compilable / runnable. For the following example, I had to change parts of your fun:
fun main() {
println(formatDuration(364.34))
}
fun formatDuration(duration: Double): String {
val minutes = duration.toInt() / 60
// fill the result to be of 2 characters, use 0 as padding char
return minutes.toString().padStart(2, '0')
}
Executing this results in the output 06.
Alternatively, you can simply use String.format() from Java, just
return "%02d".format(minutes)
instead of return minutes.toString().padStart(2, '0'), the result stays the same.
You can achive this with padStart
Example:
val padWithSpace = "125".padStart(5)
println("'$padWithSpace'") // ' 125'
val padWithChar = "a".padStart(5, '.')
println("'$padWithChar'") // '....a'
// string is returned as is, when its length is greater than the specified
val noPadding = "abcde".padStart(3)
println("'$noPadding'") // 'abcde'

How to create String with certain length and same value effectively in Kotlin

I knew this can be achieved with for loop but I am looking for better solution.
createDummyString(1,'A') = 'A'
createDummyString(2.'A') = 'AA'
This will be used in hangman. Thank you.
You can do it like in the example below. To learn more about Strings read this: https://kotlinlang.org/api/latest/jvm/stdlib/kotlin/-string/index.html
fun createDummyString(repeat : Int, alpha : Char) = alpha.toString().repeat(repeat)
Addendum:
If you want to make it more kotlinesque, you can also define repeat as extension function on Char
fun Char.repeat(count: Int): String = this.toString().repeat(count)
and call it like this:
'A'.repeat(1)
CharSequence has an extension method for this.
fun CharSequence.repeat(n: Int): String // for any whole number
Example
println("A".repeat(4)) // AAAA
println("A".repeat(0)) // nothing
println("A".repeat(-1)) // Exception
Reference : https://kotlinlang.org/api/latest/jvm/stdlib/kotlin.text/repeat.html
I created a utility function using infix operator for this :
infix fun Int.times(s : CharSequence): CharSequence{
return s.repeat(this)
}
//Use like val twoAs = 2 times "A"
println(a) // AA

Can you map/reduce a String into an Int?

I was solving a problem on codeforces in which I had to sum up the digits of a big number (it can have up to 100k digits) and I'd have to repeat that process until there is only one digit left and count the number of times I did that and I came up with a working solution, however I'd like to know if some things could have been done in a more "Kotlin-ish like way", so given:
fun main(args: Array<String>) {
println(transform(readLine()!!))
}
fun transform(n: String): Int {
var count = 0
var sum : Int
var s = n
while(s.length > 1) {
sum = (0 until s.length).sumBy { s[it].toInt() - '0'.toInt() }
s = sum.toString()
count++
}
return count
}
sum = (0 until s.length).sumBy { s[it].toInt() - '0'.toInt() } is there a way to I guess map the sum of digits in the string to the sum variable, or in general a better approach than the one I used?
When converting a Char to an Int it converts it to the ASCII value so I had to add "-'0'.toInt()" is there a faster way (not that it's too much to write, asking out of curiosity)?
How to make the String n mutable without creating a new String s and manipulating it? Or is that the desired (and only) way?
P.S. I'm a beginner with Kotlin.
When converting a Char to an Int it converts it to the ASCII value so I had to add "-'0'.toInt()" is there a faster way (not that it's too much to write, asking out of curiosity)?
You can simply write s[it] - '0', because subtracting Chars in Kotlin already gives you an Int:
public class Char ... {
...
/** Subtracts the other Char value from this value resulting an Int. */
public operator fun minus(other: Char): Int
...
}
But why are looping over the indexes when you could loop over the Chars directly?
sum = s.sumBy { it - '0' }
This is a functional (and recursive) style to solve it:
private fun sum(num: String, count: Int) : Int {
return num
//digit to int
.map { "$it".toInt() }
//sum digits
.sum()
//sum to string
.toString()
//if sum's length is more than one, do it again with incremented count. Otherwise, return the current count
.let { if (it.length > 1) sum(it, count + 1) else count }
}
And you call it like this:
val number = "2937649827364918308623946..." //and so on
val count = sum(number, 0)
Hope it helps!