我的二进制搜索应用程序不在这里
Is my application of binary search not right here?
所以,我正在解决这个问题:http://www.spoj.com/problems/IMMERSED/
一个奇妙的发现即将在生物学领域发生,而你是进行研究的团队的一员。这项研究是关于测量细胞在无氧气和有毒物质存在的环境中的生长。研究小组得出了一个恶毒的假设,分析数据告诉他们:生长、天数和毒性;与以下公式相关:
p=N*NcN;
其中p是在数千个细胞中测量的生长。
N是经过的天数。
c是与实验毒性水平相关的常数。
当这些细胞达到特定生长时,你的生物学伙伴需要从这些细胞中取出一些组织。他们要求你编写一个程序,告诉他们发生这种情况的确切时间,考虑到毒性水平和所需的生长。
输入
第一行是T(1≤T≤40000),测试用例的数量,然后是T
每个测试用例都是一行,其中有2个整数(Pc),用空格分隔。
p(1≤p≤1015)
c(1≤c≤5)
输出
对于每个测试用例,您必须以十进制格式输出预期时间。
我所做的是使用二进制搜索来查找天数,如下所示:
#define eps 1e-7
const double cont = 14.0;
double p,c;
double binary (double start, double end);
double func (double n);
int main (void)
{
int t;
cin>>t;
while (t != 0)
{
cin>>p>>c;
double mid,ans,start=0,end=cont;
ans = binary(start,end);
cout.precision(6);
cout<<fixed<<ans<<"n";
t--;
}
return 0;
}
double func (double n)
{
double ret = n*pow(n,c*n);
return ret;
}
double binary (double start, double end)
{
if (start <= end)
{
double mid = start + (end-start)/2.0;
if (func(mid)-p <= eps)
return mid;
else if (func(mid)-p > eps)
return binary(start,mid);
else
return binary(mid,end);
}
}
然而,在运行我的代码时,它甚至在给定的测试用例中给出了错误的答案,这些测试用例是:
Input:
3
1 1
3 4
100 1
Output:
1.000000
1.207384
3.086308
My output (for the above input)
0.875
0.875
1.75
附言:我没有张贴图书馆和所有为了避免混乱。此外,一旦得到正确的值,我会将其设置为小数点后6位。我只想知道,是我的逻辑不正确,还是我的二进制搜索实现不正确?
编辑:我提交的新代码
double binary (double start, double end)
{
if (start <= end)
{
double mid = start + (end-start)/2.0;
double delta = func(mid) - p;
if (delta < -1*eps)
return binary(mid,end);
else if (delta > eps)
return binary(start,mid);
else
return mid;
}
}
您的测试顺序不合理:
if (func(mid)-p <= eps)
return mid;
else if (func(mid)-p > eps)
return binary(start,mid);
else
return binary(mid,end);
尝试
if (func(mid)-p < -eps)
return binary(mid,end);
else if (func(mid)-p > eps)
return binary(start,mid);
else
return mid;
我也不确定这两个递归调用。我保留了你的逻辑(因为我可能误解了你的公式),但他们回头看我
我确信的是,您应该在内部案例(实际上是abs(func(mid)-p) < eps
)之前测试(并使用递归调用)两个外部案例(func(mid)-p < -eps
和func(mid)-p > eps
)
编辑:更干净(更快)的二进制搜索版本是:
double binary (double start, double end)
{
for (;;)
{
double mid = (start + end) * .5;
double delta=func(mid)-p;
if ( delta < -eps)
start = mid;
else if (delta > eps)
end = mid;
else
return mid;
}
}
牛顿搜索可能比这更快。
除了解释搜索JSF的问题外,您还可以更准确地计算方法
您需要精度为10^-6的N
。对于您的实现,您一直在搜索,直到找到P
的值,精度为10^-7。由于函数是指数函数,因此非常陡峭,即P
随N
变化非常快,这将导致比必要的计算量多得多的计算。
相反,您应该有一个停止条件end - start < 1e-6
。
现在我有一个语义问题:10^-6的准确性是否意味着所有数字都必须正确,或者最后一个数字是否允许偏离1?如果允许的话,停止后start
或end
将是一个很好的答案。如果没有,您可以将它们向上四舍五入,精确到10^-6。您应该四舍五入,因为该语句可能要求第一个N
,其中func(N) > P
,而不是等式的近似值。然后,如果它们不同,请检查start
的四舍五入值是否满足该语句。如果是,则输出;如果不是,则输出end
的四舍五入值。
给定14.0的上界,搜索空间仅为14.0 / 1e-6 = 1.4 * 10^8
元素。它的基2日志刚刚超过27,所以每个测试用例只需要28次迭代(如果计算更准确的上限,可能需要27次)。这绝对不需要复杂的优化才能通过。
- WM_CTLCOLORSTATIC从未在WIN32应用程序中触发
- 如何在实时应用程序中锁定线程
- 在 Flutter 应用程序中使用 Android NDK 中的 AssetManager 类
- 视窗 10 :笔(手写笔)在 MFC 应用程序上不起作用
- 无法在 consol 应用程序中更新窗口
- 在iOS应用程序中创建数据库
- Qt-png图像未显示在部署应用程序中
- 如何在控制台应用程序中添加滚动功能以显示更大的输入
- 在大型应用程序的main上使用try-catch
- 在Qt应用程序中包含Python.h会导致对Qt函数的未定义引用
- 需要有关在qt c ++应用程序中使用崩溃问题的建议
- 如何隐藏最大化和最小化按钮并在qml应用程序窗口中显示关闭按钮?
- 在 MFC 应用程序中实现 IServiceProvider
- 在 Win32 应用程序中承载 GTK+3 上下文
- 单声道嵌入在 qt 5.3 应用程序中
- 为什么无法在 Cocoa 应用程序调用的 C++ func 中嵌入自定义 Python 模块
- 在关闭应用程序期间正确关闭线程,该线程可能会运行很长时间的循环
- Xlib XSENDEVENT在其他应用程序/过程中
- QWebView 用于在桌面应用程序中运行 javascript (D3) - 当 HTML 更改时重新加载速度很慢
- 在GLFW应用程序中,std::cin的行为很奇怪