Есть ли способ перебрать десятичную часть двойной переменной в swift 4? - PullRequest
1 голос
/ 28 июня 2019

Что я ищу:

Учитывая Double (doublenumber) и Int (n), я хочу перебрать через 1-е десятичное, 2-е десятичное, 3-е десятичное, 4-е десятичное .... до десятичного числа 'n'

Мой первый подход заключался в покрытии String of Double, чтобы я мог перебирать как массив строку, но проблема в том, что при преобразовании в строку я теряю много десятичных чисел

    let doubleNumber = 1.00/98                  //0.010204081632653061224489795918367346938775510204081632653...
    var stringFromDouble = String(doubleNumber) //0.010204081632653
    stringFromDouble.removeFirst()              //.010204081632653
    stringFromDouble.removeFirst()              //010204081632653

    for letter in stringFromDouble{
      //cycle to iterate the decimals
    }

1 Ответ

3 голосов
/ 28 июня 2019

Если намерение состоит в том, чтобы получить много десятичных цифр 1.0/98.0, то вы не должны сохранять это число в Double, поскольку оно имеет точность только приблизительно 16 десятичных цифр. , Вы можете использовать Decimal с точностью до 38 десятичных цифр.

Но для получения более десятичных цифр вам придется выполнять «рациональную арифметику», то есть работать с числителем и знаменателем дроби как целых чисел.

Вот как вы можете вывести произвольное количество десятичных цифр рационального числа. Для простоты я предположил, что число положительное и меньше единицы.

func printDecimalDigits(of numerator: Int, dividedBy denominator: Int, count: Int) {
    var numerator = numerator
    for _ in 1...count {
        // Multiply by 10 to get the next digit:
        numerator *= 10
        // Print integer part of `numerator/denominator`:
        print(numerator / denominator, terminator: "")
        // Reduce `numerator/denominator` to its fractional part:
        numerator %= denominator
    }
    print()
}

Пример:

printDecimalDigits(of: 1, dividedBy: 98, count: 100)
// 0102040816326530612244897959183673469387755102040816326530612244897959183673469387755102040816326530

Или как функция, которая возвращает цифры в виде (с ленивой оценкой) последовательность:

func decimalDigits(of numerator: Int, dividedBy denominator: Int) -> AnySequence<Int> {
    return AnySequence(sequence(state: numerator) { num -> Int in
        num *= 10
        let d = num / denominator
        num %= denominator
        return d
    })
}
* * 1 022 Пример: * 1 023 *
let first1000Digits = decimalDigits(of: 1, dividedBy: 98).prefix(1000)
for d in first1000Digits { print(d) }
...