字符串声明/引用参数的困难(c ++)

时间:2017-01-15 15:23:46

标签: c++ string reference-parameters

上周我写了一个函数来编写一个函数:函数得到一个string和一个char值,并且应该在现有char的第一次出现之前和之后将字符串分成两部分。 。

代码工作但我的老师告诉我再做一次,因为代码编写得不好。但我不明白如何让它变得更好。到目前为止,我理解用白色空格定义两个字符串并不好,但除此之外我还会超出范围。由于字符串输入发生变化,字符串大小每次都会改变。

#include <iostream>
#include <string>
using namespace std;

void divide(char search, string text, string& first_part, string& sec_part) 
{
    bool firstc = true;
    int counter = 0;

    for (int i = 0; i < text.size(); i++) {
        if (text.at(i) != search && firstc) {
            first_part.at(i) = text.at(i);
        }
        else if (text.at(i) == search&& firstc == true) {
            firstc = false;
            sec_part.at(counter) = text.at(i);
        }
        else {
            sec_part.at(counter) = text.at(i);
            counter++;
        }
    }
}

int main() {
    string text;
    string part1="                            ";
    string part2="                            ";
    char search_char;   

    cout << "Please enter text? ";
    getline(cin, text);

    cout << "Please enter a char: ? ";
    cin >> search_char;

    divide(search_char,text,aprt1,part2);
    cout << "First string: " << part1 <<endl;
    cout << "Second string: " << part2 << endl;

    system("PAUSE");
    return 0;
}

5 个答案:

答案 0 :(得分:1)

我建议你学习使用c ++标准函数。有很多实用功能可以帮助你编程。

void divide(const std::string& text, char search, std::string& first_part, std::string& sec_part)
{
    std::string::const_iterator pos = std::find(text.begin(), text.end(), search);

    first_part.append(text, 0, pos - text.begin());
    sec_part.append(text, pos - text.begin());
}

int main()
{
    std::string text = "thisisfirst";
    char search = 'f';

    std::string first;
    std::string second;

    divide(text, search, first, second);
}

我在std::find使用了Iterators,您可以从hereconst阅读相关内容。

你还有其他一些错误。您将按值传递文本,每次调用函数时都会执行复制。通过引用传递它,但用<html> <head> </head> <body> ...//page markup <script src="dist/myCodeAsES5.js"></script> <script> var obj = new MyClass(); obj.calculate(); </script> </body> </html> 限定它,表明它是输入参数而不是输出。

答案 1 :(得分:1)

只有在part1.length()中找到该字符时,您的代码才能正常工作。你需要类似的东西:

void string_split_once(const char s, const string & text, string & first, string & second) {
    first.clear();
    second.clear();
    std::size_t pos = str.find(s);
    if (pos != string::npos) {
        first  = text.substr(0, pos);
        second = text.substr(pos);
    }

}

答案 2 :(得分:1)

正如您自己了解这些声明

class ResourceLoader {

getHomeScreen() {
    var homeData = BASEURL + "/home.json";
    var homeTemplate = BASEURL + "/home.tvml";

    this.getRemoteJSON(homeData, homeTemplate, this._jsonLoaded);
}

_jsonLoaded(template, jsonString) {
    var parsedJSON = JSON.parse(jsonString);
    this.getRemoteXMLFile(template, parsedJSON);
}

getRemoteJSON(file, template, callback) {
    var xhr = new XMLHttpRequest();
    xhr.responseType = "text";
    xhr.addEventListener("load", function() {
        callback(template, xhr.responseText);
    }, false);
    xhr.open("GET", file, true);
    xhr.send();
}

getRemoteXMLFile(template, json) {
    var xhr = new XMLHttpRequest();
    xhr.responseType = "xml";
    xhr.addEventListener("load", function() {
        loadRemoteFile(xhr.responseText, json);
    }, false);
    xhr.open("GET", template, true);
    xhr.send();
}

}

没有意义,因为对象string part1=" "; string part2=" "; 中输入的字符串基本上可以超过两个初始化字符串。在这种情况下,使用字符串方法text可能会导致抛出异常,或者字符串将具有尾随空格。

从作业的描述中,不清楚搜索到的字符是否应该包含在其中一个字符串中。您认为该字符应包含在第二个字符串中。

考虑到参数at应该被声明为常量引用。

此外,不使用循环,最好使用类text的方法,例如std::string

该功能可以按以下方式查看

find

程序输出

#include <iostream>
#include <string>

void divide(const std::string &text, char search, std::string &first_part, std::string &sec_part)
{
    std::string::size_type pos = text.find(search);

    first_part = text.substr(0, pos);

    if (pos == std::string::npos)
    {
        sec_part.clear();
    }
    else
    {
        sec_part = text.substr(pos);
    }
}

int main()
{   
    std::string text("Hello World");
    std::string first_part;
    std::string sec_part;

    divide(text, ' ', first_part, sec_part);

    std::cout << "\"" << text << "\"\n";
    std::cout << "\"" << first_part << "\"\n";
    std::cout << "\"" << sec_part << "\"\n";
}

正如你所看到的那样,分隔字符包含在第二个字符串中,尽管我认为从两个字符串中排除它可能会更好。

另一种选择,在我看来,更清晰的方法可以采用以下方式

"Hello World"
"Hello"
" World"

答案 3 :(得分:1)

为什么你的老师是对的?

您需要使用空格空间初始化目标字符串这一事实非常糟糕:

  • 如果输入字符串较长,则会出现超出范围的错误。
  • 如果它更短,则答案错误,因为在IT和编程中, "It works ""It works" 不同。

此外,您的代码不符合规范。它应始终工作,与输出字符串中存储的当前值无关。

备选方案1:您的代码但正在运作

只需在开头清除目标字符串即可。然后像你一样迭代,但使用+=push_back()在字符串的末尾添加字符。

void divide(char search, string text, string& first_part, string& sec_part) 
{
    bool firstc = true;
    first_part.clear();   // make destinations strings empty
    sec_part.clear();  

    for (int i = 0; i < text.size(); i++) {
        char c = text.at(i); 
        if (firstc && c != search) {
            first_part += c;
        }
        else if (firstc && c == search) {
            firstc = false;
            sec_part += c;
        }
        else {
            sec_part += c;
        }
    }
}

我使用了临时c而不是text.at(i)text\[i\],以避免多重索引但是这并不是真正需要的:现在,优化编译器应该生成等效的代码,无论变体是什么你在这里使用

备选方案2:使用字符串成员函数

此替代方法使用find()函数,然后从开始到该位置构造一个字符串,并从该位置构造另一个字符串。没有找到角色时有一种特殊情况。

void divide(char search, string text, string& first_part, string& sec_part) 
{
    auto pos = text.find(search); 
    first_part = string(text, 0, pos);
    if (pos== string::npos) 
        sec_part.clear(); 
    else sec_part = string(text, pos,  string::npos); 
}

答案 4 :(得分:0)

我看到的最大问题是您使用的at应该使用push_back。见std::basic_string::push_backat旨在访问现有字符以读取或修改它。 push_back在字符串中附加一个新字符。

divide可能如下所示:

void divide(char search, string text, string& first_part,
            string& sec_part)
{
    bool firstc = true;

    for (int i = 0; i < text.size(); i++) {
        if (text.at(i) != search && firstc) {
            first_part.push_back(text.at(i));
        }
        else if (text.at(i) == search&& firstc == true) {
            firstc = false;
            sec_part.push_back(text.at(i));
        }
        else {
            sec_part.push_back(text.at(i));
        }
    }
}

由于您不处理异常,请考虑使用text[i]而不是text.at(i)