Общий метод, который может вернуть случайное целое число между двумя параметрами, такими как ruby, с rand(0..n).
Любое предложение?
Общий метод, который может вернуть случайное целое число между двумя параметрами, такими как ruby, с rand(0..n).
Любое предложение?
Моим предложением была бы функция расширения в IntRange для создания случайных типов, таких как: (0..10).random()
Начиная с версии 1.3, Kotlin поставляется с собственным многоплатформенным генератором случайных чисел. Это описано в этом разделе. Расширение, описанное ниже, теперь является частью стандартной библиотеки Kotlin, просто используйте его следующим образом:
val rnds = (0..10).random()
До версии 1.3 в JVM мы использовали Random или даже ThreadLocalRandom если мы находимся на JDK> 1.6.
fun IntRange.random() =
Random().nextInt((endInclusive + 1) - start) + start
Используется так:
// will return an 'Int' between 0 and 10 (incl.)
(0..10).random()
Если вы хотите, чтобы функция возвращала только 1, 2,..., 9 (10 не включено), используйте диапазон, созданный until:
(0 until 10).random()
Если вы работаете с JDK> 1.6, используйте ThreadLocalRandom.current() вместо Random().
KotlinJs и другие варианты
Для kotlinjs и других вариантов использования, которые не позволяют использовать java.util.Random, см. Эту альтернативу.
Также см. Этот ответ для вариантов моего предложения. Он также включает в себя функцию расширения для случайных Char.
Создайте случайное целое число от from (включительно) и to (исключая)
import java.util.Random
val random = Random()
fun rand(from: Int, to: Int) : Int {
return random.nextInt(to - from) + from
}
Что касается kotlin 1.2, вы можете написать:
(1..3).shuffled().last()
Просто знайте, что это большой O (n), но для небольшого списка (особенно уникальных значений) это хорошо: D
Вы можете создать функцию расширения, аналогичную java.util.Random.nextInt(int) но тот, который принимает IntRange вместо Int для своей привязки:
fun Random.nextInt(range: IntRange): Int {
return range.start + nextInt(range.last - range.start)
}
Теперь вы можете использовать это с любым Random экземпляром:
val random = Random()
println(random.nextInt(5..9)) // prints 5, 6, 7, or 8
Если вы не хотите управлять своим собственным экземпляром Random, тогда вы можете определить метод удобства, используя, например, ThreadLocalRandom.current():
fun rand(range: IntRange): Int {
return ThreadLocalRandom.current().nextInt(range)
}
Теперь вы можете получить случайное целое число, как в Ruby, без необходимости сначала объявлять экземпляр Random самостоятельно:
rand(5..9) // returns 5, 6, 7, or 8
Возможное изменение моего другого ответа для случайных символов
Чтобы получить случайные Char, вы можете определить такую функцию расширения, как эта
fun ClosedRange<Char>.random(): Char =
(Random().nextInt(endInclusive.toInt() + 1 - start.toInt()) + start.toInt()).toChar()
// will return a 'Char' between A and Z (incl.)
('A'..'Z').random()
Если вы работаете с JDK> 1.6, используйте ThreadLocalRandom.current() вместо Random().
Этот ответ поможет для kotlinjs и других случаев использования, которые не позволяют использовать java.util.Random.
Начиная с версии 1.3, Kotlin поставляется с собственным мультиплатформенным генератором случайных чисел. Это описано в этом разделе. Теперь вы можете напрямую использовать расширение как часть стандартной библиотеки Kotlin, не определяя его:
('a'..'b').random()
Создание @s1m0nw1 отличного ответа. Я внес следующие изменения.
код:
private object RandomRangeSingleton : Random()
fun ClosedRange<Int>.random() = RandomRangeSingleton.nextInt((endInclusive + 1) - start) + start
Тестовый пример:
fun testRandom() {
Assert.assertTrue(
(0..1000).all {
(0..5).contains((0..5).random())
}
)
Assert.assertTrue(
(0..1000).all {
(0..4).contains((0 until 5).random())
}
)
Assert.assertFalse(
(0..1000).all {
(0..4).contains((0..5).random())
}
)
}
Примеры случайных в диапазоне [1, 10]
val random1 = (0..10).shuffled().last()
или использование Java Random
val random2 = Random().nextInt(10) + 1
Начиная с версии 1.3 стандартная библиотека обеспечивала многоплатформенную поддержку случайных типов, см. Этот ответ.
Если вы работаете с Kotlin JavaScript и не имеете доступа к java.util.Random, будет работать следующее:
fun IntRange.random() = (Math.random() * ((endInclusive + 1) - start) + start).toInt()
Используется так:
// will return an 'Int' between 0 and 10 (incl.)
(0..10).random()
Другой способ реализации ответа s1m0nw1 - получить к нему доступ через переменную. Не то чтобы это более эффективно, но избавляет вас от необходимости печатать().
val ClosedRange<Int>.random: Int
get() = Random().nextInt((endInclusive + 1) - start) + start
И теперь к нему можно получить доступ как таковой
(1..10).random
Нет стандартного метода, который делает это, но вы можете легко создать свой собственный, используя либо Math.random(), либо класс java.util.Random. Ниже приведен пример использования метода Math.random():
fun random(n: Int) = (Math.random() * n).toInt()
fun random(from: Int, to: Int) = (Math.random() * (to - from) + from).toInt()
fun random(pair: Pair<Int, Int>) = random(pair.first, pair.second)
fun main(args: Array<String>) {
val n = 10
val rand1 = random(n)
val rand2 = random(5, n)
val rand3 = random(5 to n)
println(List(10) { random(n) })
println(List(10) { random(5 to n) })
}
Это пример вывода:
[9, 8, 1, 7, 5, 6, 9, 8, 1, 9]
[5, 8, 9, 7, 6, 6, 8, 6, 7, 9]
Используя функцию верхнего уровня, вы можете получить тот же синтаксис вызова, что и в Ruby (по вашему желанию):
fun rand(s: Int, e: Int) = Random.nextInt(s, e + 1)
Использование:
rand(1, 3) // returns either 1, 2 or 3
Если числа, которые вы хотите выбрать, не являются последовательными, вы можете использовать random().
Использование:
val list = listOf(3, 1, 4, 5)
val number = list.random()
Возвращает одно из чисел, которые есть в списке.
Во-первых, вам нужен RNG. В Котлине вам в настоящее время нужно использовать специфичные для платформы (в одном из них нет котлина). Для JVM это java.util.Random. Вам нужно создать экземпляр, а затем вызвать random.nextInt(n).
Стандартная библиотека Kotlin не предоставляет API генератора случайных чисел. Если вы не в мультиплатформенном проекте, лучше использовать платформу api (все остальные ответы на вопрос об этом решении).
Но если вы находитесь в мультиплатформенном контексте, лучшим решением является реализовать случайное для себя в чистом kotlin для совместного использования одного и того же генератора случайных чисел между платформами. Это проще для разработчиков и тестирования.
Чтобы ответить на эту проблему в моем личном проекте, я реализую чистый линейный конгруэнтный генератор Kotlin . LCG - это алгоритм, используемый java.util.Random. Следуйте этой ссылке, если вы хотите ее использовать:
https://gist.github.com/11e5ddb567786af0ed1ae4d7f57441d4
Моя цель реализации nextInt(range: IntRange) для вас;).
Позаботьтесь о своей цели, LCG хорош для большинства случаев использования (имитация, игры и т.д.), но не подходит для криптографического использования из-за предсказуемости этого метода.
В Kotlin 1.3 вы можете сделать это как
val number = Random.nextInt(limit)
Больше не нужно использовать пользовательские функции расширения. IntRange теперь имеет встроенную функцию расширения random().
val randomNumber = (0..10).random()
Подход первый:
val randomInteger = (1..10).shuffled().first()
//or randomInteger = (1..10).shuffled().last()
fun main() {
print(randomInteger)
}
// Result: 4
Подход второй:
val randomInteger = (Math.random() * 10).toInt() + 1
fun main() {
print(randomInteger)
}
// Result: 10
Подход третий:
val randomInteger = (1 until 11).random()
fun main() {
print(randomInteger)
}
// Result: 8
Подход четвертый:
import java.util.Random
val randomInteger = Random().nextInt(10) + 1
fun main() {
print(randomInteger)
}
// Result: 1
Надеюсь это поможет.
Чтобы получить случайное число Int в Kotlin, используйте следующий метод:
import java.util.concurrent.ThreadLocalRandom
fun randomInt(rangeFirstNum:Int, rangeLastNum:Int) {
val randomInteger = ThreadLocalRandom.current().nextInt(rangeFirstNum,rangeLastNum)
println(randomInteger)
}
fun main() {
randomInt(1,10)
}
// Result – random Int numbers from 1 to 9
Надеюсь это поможет.
Вы можете создать функцию расширения:
infix fun ClosedRange<Float>.step(step: Float): Iterable<Float> {
require(start.isFinite())
require(endInclusive.isFinite())
require(step.round() > 0.0) { "Step must be positive, was: $step." }
require(start != endInclusive) { "Start and endInclusive must not be the same"}
if (endInclusive > start) {
return generateSequence(start) { previous ->
if (previous == Float.POSITIVE_INFINITY) [email protected] null
val next = previous + step.round()
if (next > endInclusive) null else next.round()
}.asIterable()
}
return generateSequence(start) { previous ->
if (previous == Float.NEGATIVE_INFINITY) [email protected] null
val next = previous - step.round()
if (next < endInclusive) null else next.round()
}.asIterable()
}
Значение Round Float:
fun Float.round(decimals: Int = DIGITS): Float {
var multiplier = 1.0f
repeat(decimals) { multiplier *= 10 }
return round(this * multiplier) / multiplier
}
Использование метода:
(0.0f .. 1.0f).step(.1f).forEach { System.out.println("value: $it") }
Выход:
значение: 0,0 значение: 0,1 значение: 0,2 значение: 0,3 значение: 0,4 значение: 0,5 значение: 0,6 значение: 0,7 значение: 0,8 значение: 0,9 значение: 1,0
быть супер пупер))
fun rnd_int(min: Int, max: Int): Int {
var max = max
max -= min
return (Math.random() * ++max).toInt() + min
}