Co.*_*den 37 .net c# decimal factorial
有没有办法比较两个数字中哪个阶乘数更大而不计算?
场景是我正在创建ac#console应用程序,它需要两个因子输入
123!!!!!!
456!!!
Run Code Online (Sandbox Code Playgroud)
我想要做的就是比较哪个阶乘值大于其他因素,我所做的代码片段
try
{
string st = Console.ReadLine();
Int64 factCount = 0;
while (st.Contains('!'))
{
factCount = st.Where(w => w == '!').Count();
st = st.Replace('!', ' ');
};
decimal result = 1 ;
for (Int64 j = 0; j < factCount; j++)
{
UInt64 num = Convert.ToUInt64(st.Trim());
for (UInt64 x = num; x > 0; x--)
{
result = result * x;
}
}
if (factCount == 0)
{
result = Convert.ToUInt64(st.Trim());
}
string st2 = Console.ReadLine();
Int64 factCount2 = 0;
while (st2.Contains('!'))
{
factCount2 = st2.Where(w => w == '!').Count();
st2 = st2.Replace('!', ' ');
};
decimal result2 = 1;
for (Int64 j = 0; j < factCount2; j++)
{
UInt64 num = Convert.ToUInt64(st.Trim());
for (UInt64 x = num; x > 0; x--)
{
result2 = result2 * x;
}
}
if (factCount2 == 0)
{
result2 = Convert.ToUInt64(st2.Trim());
}
if (result == result2)
{
Console.WriteLine("x=y");
}
else if (result < result2)
{
Console.WriteLine("x<y");
}
else if (result > result2)
{
Console.WriteLine("x>y");
}
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
Console.ReadLine();
}
Run Code Online (Sandbox Code Playgroud)
但我得到的错误是
值太大或太小十进制
我理解错误但有任何方法来做到这一点
请建议是否有任何其他数据类型可以容纳大于十进制的值,或者是否有任何其他方法来比较这些因子
实现@Bathsheba建议后,我改变了一些代码
string st = Console.ReadLine();
int factCount = 0;
while (st.Contains('!'))
{
factCount = st.Where(w => w == '!').Count();
st = st.Replace('!', ' ');
};
string st2 = Console.ReadLine();
int factCount2 = 0;
while (st2.Contains('!'))
{
factCount2 = st2.Where(w => w == '!').Count();
st2 = st2.Replace('!', ' ');
};
int resultFactCount = factCount - factCount2;
decimal result = 1;
decimal result2 = 1;
if (resultFactCount > 0)
{
for (Int64 j = 0; j < resultFactCount; j++)
{
UInt64 num = Convert.ToUInt64(st.Trim());
for (UInt64 x = num; x > 0; x--)
{
result = result * x;
}
}
if (factCount == 0)
{
result = Convert.ToUInt64(st.Trim());
}
UInt64 num1 = Convert.ToUInt64(st.Trim());
if (result == num1)
{
Console.WriteLine("x=y");
}
else if (result < num1)
{
Console.WriteLine("x<y");
}
else if (result > num1)
{
Console.WriteLine("x>y");
}
}
else
{
int resultFactCount1 = System.Math.Abs(resultFactCount);
for (Int64 j = 0; j < resultFactCount1; j++)
{
UInt64 num = Convert.ToUInt64(st.Trim());
for (UInt64 x = num; x > 0; x--)
{
result2 = result2 * x;
}
}
if (factCount2 == 0)
{
result2 = Convert.ToUInt64(st2.Trim());
}
UInt64 num1 = Convert.ToUInt64(st.Trim());
if (result2 == num1)
{
Console.WriteLine("x=y");
}
else if (result2 < num1)
{
Console.WriteLine("x<y");
}
else if (result2 > num1)
{
Console.WriteLine("x>y");
}
}
Run Code Online (Sandbox Code Playgroud)
很抱歉,但仍然是123 !!! 是如此巨大,我得到了同样的错误
传统上
m!!...!用n!s表示m(m-n)(m-2n)....但是这里被当作(...((m!)!)!...)!
注亚历克,是的,我知道,这是一个不幸的符号,但是你看到的传统定义是有用得多(在组合,其中阶乘来自的地方),比一个的OP想.
我会把它放在评论中,但它会被其他人黯然失色,这非常重要.
Bat*_*eba 52
在这里,a!!定义为(a!)!.
123!!!!!!绝对是巨大的.如果你用墨水写下来的话,我认为你需要更多的粒子而不是宇宙中的粒子.
因此,您无法直接比较这些数字.我认为没有一个数字类可以做到这一点.
你可以做的是考虑商123!!!!!! / 456!!!.许多倍数都是相似的,所以你可以取消它们.另请注意,尾随!将取消.这是因为x> y暗示,并且暗示为x!>你!其中x和y是正整数.
最终,您将达到可以将其评估为小于或大于1的点,从而得出您的答案.
我可以告诉你,在检查这123!!!!!!是更大的,因为123!!!大于456.
Per*_*t28 22
与其他答案不同,您可以不做任何近似.
这里是 :
123 !!!!!! > 456 !!!
Run Code Online (Sandbox Code Playgroud)
实际上意味着
123 !!!!! > 456 !!
123 !!!! > 456 !
Run Code Online (Sandbox Code Playgroud)
并且
123 !!! > 456
Run Code Online (Sandbox Code Playgroud)
所以你只需要证明上面的内容.这很简单,因为你至少有一个可以适合的操作数 UInt64
所以这应该给你这样的东西:
public class Program
{
static bool LeftIsGreaterThanRightSide(UInt64 leftSide, int leftSidefactCount, UInt64 rightSide)
{
try
{
checked // for the OverflowException
{
UInt64 input2 = leftSide;
int factCount = leftSidefactCount;
UInt64 result = 1;
for (Int64 j = 0; j < factCount; j++)
{
UInt64 num = input2;
for (UInt64 x = num; x > 0; x--)
{
result = result * x;
}
}
// None of the operand are great or equal than UInt64.MaxValue
// So let's compare the result normaly
return result > rightSide;
}
}
catch (OverflowException)
{
// leftSide overflowed, rightSide is a representable UInt64 so leftSide > rightSide ;
return true;
}
}
static void Main()
{
String input1 = Console.ReadLine();
String input2 = Console.ReadLine();
int fact1Count = input1.Count(c => c == '!');
int fact2Count = input2.Count(c => c == '!');
UInt64 x = Convert.ToUInt64(input1.Replace("!", String.Empty).Trim());
UInt64 y = Convert.ToUInt64(input2.Replace("!", String.Empty).Trim());
x = x == 0 ? 1 : x ; // Handling 0 !
y = y == 0 ? 1 : y;
if (fact1Count > fact2Count)
{
fact1Count = fact1Count - fact2Count;
Console.WriteLine(LeftIsGreaterThanRightSide(x, fact1Count, y) ? "x > y" : "x <= y");
}
else
{
fact2Count = fact2Count - fact1Count;
Console.WriteLine(LeftIsGreaterThanRightSide(y, fact2Count, x) ? "y > x" : "y <= x");
}
Console.ReadLine();
}
}
Run Code Online (Sandbox Code Playgroud)
Dmi*_*nko 14
对于给定的数字,假设456!!!意味着((456!)!)!我们有
123!!!!!! == (123!!!)!!!
Run Code Online (Sandbox Code Playgroud)
和
123!!! >>> 456 // >>> stands for "much, much...much larger", ">>" is not enough
Run Code Online (Sandbox Code Playgroud)
甚至123!(1.2e205比)更大456
为了估计阶乘的实际值,让我们使用斯特林近似
https://en.wikipedia.org/wiki/Stirling%27s_approximation
即
ln(n!) == n * ln(n) - n
lg(n!) == ln(n!)/ln(10) == n * ln(n) / ln(10) - n / ln(10) == n * lg(n) - n / ln(10)
n! == n ** n / exp(n)
Run Code Online (Sandbox Code Playgroud)
所以((456!)!)!是关于
lg(456!) == 1014
lg((456!)!) == 1e1014 * 1014- 1e1014/ln(10) == 1e1017
lg(((456!)!)!) == 1e(1e1017)
((456!)!)! == 1e(1e(1e1017))
Run Code Online (Sandbox Code Playgroud)
这是非常庞大的数字(注意三重指数),这就是为什么不能表示为天真的BigInteger价值.
这应该很简单:
正如其他人所说,你可以删除所有常见的"!" 因为x > y <==> x! > y!
您的程序基本上必须证明阶乘(123 !!!)大于普通数字.您可以通过快速退出循环来解决此问题.在计算阶乘时,您可以在产品大于456时立即返回,因为阶乘将随着额外的迭代而增长.
// While string parsing check if one number equals 0 and has at least
// one "!" - if yes set its value to 1 ( because 0! = 1! = 1 )
int x = 123;
int y = 456;
int numberOfFactorials = 3;
try
{
for( int i = 0; i < numberOfFactorials; ++i )
{
for ( int j = x-1; j > 0; --j )
{
x *= j;
// This quick exit will return after one iteration
// because 123*122 > 456
if ( x > y ) return "x is bigger than y";
}
}
return x == y ? "gosh they are the same!"
: "x is smaller than y";
}
catch( OverflowException e )
{
return "x Overflowed so it is bigger than y!";
}
Run Code Online (Sandbox Code Playgroud)
如果要为输入参数解析更大的数字,也可以将BigInteger与此方法一起使用.
| 归档时间: |
|
| 查看次数: |
2916 次 |
| 最近记录: |