Равномерное разделение на С#
В С# как равномерно делить 100 на 7?
Таким образом, результат будет
Код ниже неверен, так как все 7 значений установлены на 15 (всего 105).
double [] vals = new double[7];
for (int i = 0; i < vals.Length; i++)
{
vals[i] = Math.Ceiling(100d / vals.Length);
}
Есть ли простой способ сделать это в С#?
Спасибо
Ответы
Ответ 1
Чтобы получить мой предложенный результат из 15, 15, 14, 14, 14, 14, 14:
// This doesn't try to cope with negative numbers :)
public static IEnumerable<int> DivideEvenly(int numerator, int denominator)
{
int rem;
int div = Math.DivRem(numerator, denominator, out rem);
for (int i=0; i < denominator; i++)
{
yield return i < rem ? div+1 : div;
}
}
Test:
foreach (int i in DivideEvenly(100, 7))
{
Console.WriteLine(i);
}
Ответ 2
Здесь вы идете:
Func<int, int, IEnumerable<int>> f = (a, b) =>
Enumerable.Range(0,a/b).Select((n) => a / b + ((a % b) <= n ? 0 : 1))
Удачи, объясняя это в классе, хотя:)
Ответ 3
Поскольку это, кажется, домашнее задание, вот подсказка, а не полный код.
Вы выполняете Math.Ceiling и преобразуете 14.28 в 15.
Ответ 4
Алгоритм - это
- Разделите 100 на 7, поместите результат в X
- Получить наивысшее четное число ниже X и поместить его в Y.
- Умножьте Y на 7 и поместите ответ в Z.
- Уберите Z от 100.
Ответ - это 6 лотов Y плюс любой результат на шаге 4.
Этот алгоритм может работать только для этого конкретного экземпляра.
Я уверен, что вы можете написать это в С#
Ответ 5
Не уверен, что это именно то, что вам нужно, но я бы подумал, что если вы используете Math.ceiling, вы всегда окажетесь слишком большим. Math.floor будет недооценивать и оставлять вас с разницей, которая может быть добавлена к одной из ваших частей по вашему усмотрению.
Например, с помощью этого метода вы можете получить 7 лотов из 14, предоставляя вам остаток 2. Затем вы можете поместить это 2 в одну из своих частей, давая вам ответ, который вы предложили, или вы можете разделить его равномерно и добавьте две части из 15 (как указано в одном из комментариев)
Ответ 6
Не уверен, почему вы работаете с двойниками, но нуждаетесь в семантике целочисленного деления.
double input = 100;
const int Buckets = 7;
double[] vals = new double[Buckets];
for (int i = 0; i < vals.Length; i++)
{
vals[i] = Math.Floor(input / Buckets);
}
double remainder = input % Buckets;
// give all of the remainder to the first value
vals[0] += remainder;
пример для int с большей гибкостью,
int input = 100;
const int Buckets = 7;
int [] vals = new int[Buckets];
for (int i = 0; i < vals.Length; i++)
{
vals[i] = input / Buckets;
}
int remainder = input % Buckets;
// give all of the remainder to the first value
vals[0] += remainder;
// If instead you wanted to distribute the remainder evenly,
// priority to first
for (int r = 0; r < remainder;r++)
{
vals[r % Buckets] += 1;
}
Стоит отметить, что двойной пример не может быть численно устойчивым, поскольку определенные входные значения и размеры ковша могут привести к утечке дробных значений.