给定字符串
s
和t
递归计算,如果t
中包含s
,则返回true
。示例:
bool find("Names Richard", "Richard") == true
;
我已经编写了下面的代码,但我不确定它是否是在C ++中使用递归的正确方法;我刚刚在课堂上学习了递归。
#include <iostream>
using namespace std;
bool find(string s, string t)
{
if (s.empty() || t.empty())
return false;
int find = static_cast<int>(s.find(t));
if (find > 0)
return true;
}
int main()
{
bool b = find("Mississippi", "sip");
string s;
if (b == 1) s = "true";
else
s = "false";
cout << s;
}
如果有人在我的代码中发现错误,请告诉我,以便我可以修复它或在哪里可以学习/阅读有关此主题的更多信息。我需要为本周三的递归测试做好准备。
答案 0 :(得分:4)
我的评论是关于看起来像这样的代码(可以递归)......
#include <iostream>
using namespace std;
bool find(string s, string t)
{
if (s.empty() || t.empty())
return false;
string start = s.substr(0, 2);
if (start == t && find(s.substr(3), t));
return true;
}
int main()
{
bool b = find("Mississippi", "sip");
string s;
if (b == 1) s = "true";
else
s = "false";
cout << s;
}
请注意:
if (start == t && find(s.substr(3), t));
return true;
这不符合你的想法。
;
语句末尾的if
会留空。无论该测试的结果如何,您的find()
函数都将返回true
。
我建议您在编译之前调高警告级别以捕获此类问题。
顺便说一句,我发现在每个代码块周围使用大括号,甚至是单行块,可以帮助我避免这种错误。
您的代码中还有其他错误。从2
中删除幻数3
和find()
将鼓励您思考它们代表的内容并指出正确的道路。
您希望start == t && find(s.substr(3), t)
如何运作?如果你能用简单的英语(或你的母语)表达一个算法,你就有更高的机会用C ++表达它。
此外,我建议添加应返回false
的测试用例(例如find("satsuma", "onion")
)以确保您的代码与应返回true
的调用一样有效。
最后一条建议是风格化的,像这样放置你的代码会使你测试的布尔表达式更加明显,而不需要求助于临时并与1
进行比较:
int main()
{
std::string s;
if (find("Mississippi", "sip"))
{
s = "true";
}
else
{
s = "false";
}
std::cout << s << std::endl;
}
祝你上课好运!
答案 1 :(得分:2)
你的递归函数需要两件事:
这是一个快速分析:
bool find(string s, string t)
{
if (s.empty() || t.empty()) //definite condition of failure. Good
return false;
string start = s.substr(0, 2);
if (start == t && find(s.substr(3), t)); //mixed up definition of success and recursive call
return true;
}
请改为尝试:
bool find(string s, string t)
{
if (s.empty() || t.empty()) //definite condition of failure. Done!
return false;
string start = s.substr(0, 2);
if (start == t) //definite condition of success. Done!
return true;
else
return find(s.substr(3), t) //simply the problem and return whatever it finds
}
答案 2 :(得分:0)
你说的是正确的 - 只要函数调用自己就可以说它是递归的 - 但即使是最简单的测试也应该告诉你代码不能正常工作。例如,将"sip"
更改为"sipx"
,它仍会输出true
。你编译并运行这个程序了吗?您是否使用各种不同的输入进行了测试?
答案 3 :(得分:0)
您没有使用递归。在你的函数中使用std::string::find
感觉就像作弊(这很可能不会获得积分)。
该任务的唯一合理解释是:在不使用循环或字符串函数的情况下检查t
是否为s
的中缀。
让我们看一下这个简单的案例:Epsilon(空字)是永远字的中缀,所以如果t.empty()
成立,你必须返回true
。
否则你有两个选择:
t
可能是s
的前缀,使用递归检查很简单;只需检查t
的第一个字符是否等于s
的第一个字符,并使用其余字符串调用isPrefix
。如果返回true,则返回true。s
的第一个字符(而不是t
),然后递归(此时调用find
)。如果您遵循此配方(如果您问我,使用char const*
比使用std::string
更容易实现btw。)您将获得仅使用条件而不使用库支持的递归函数。
注意:在所有最有效的实施中,这是不,但您并没有要求提高效率,而是要求递归功能。