使用 push_back 向向量添加非空字符串,向量内容为空。为啥字符串没有添加到向量中?

Posted

技术标签:

【中文标题】使用 push_back 向向量添加非空字符串,向量内容为空。为啥字符串没有添加到向量中?【英文标题】:Adding a non-empty string to a vector using push_back, the vector contents are empty. Why is the string not added to the vector?使用 push_back 向向量添加非空字符串,向量内容为空。为什么字符串没有添加到向量中? 【发布时间】:2020-08-14 16:37:18 【问题描述】:
#include <bits/stdc++.h>
#include <string>

using namespace std;

vector<string> func(string mag) 
  vector<string> s1;
  string temp1;
  string temp2;

  temp1[0] = 'a';
  temp1[1] = 'b';
  temp1[2] = 'c';

  temp2 += "xyz";

  s1.push_back(temp1);
  s1.push_back(temp2);
  return s1;


int main() 
  string st;
  vector<string> xyz;
  xyz = func(st);

  for (int a = 0; a < xyz.size(); a++)
    cout << xyz[a] << ',';

上面代码的输出是,xyz,,尽管我期待的是abc,xyz,。不打印添加到向量中的字符串temp1

字符串temp1是非空的,打印出来输出abc,但是把它推到向量s1并打印出向量,字符串temp1不打印,而字符串@ 987654331@,其中"xyz"被添加到它作为temp2+="xyz",被添加到向量中并且在打印向量的内容时被打印。

有人可以向我解释为什么字符串temp1 没有出现在矢量内容中吗?

【问题讨论】:

无关:不要使用#include&lt;bits/stdc++.h&gt; Why is “using namespace std;” considered bad practice? 请缩进您的代码。 【参考方案1】:

string temp1; 创建一个空字符串。访问它的任何元素都是越界访问导致未定义的行为。如果您想像这样访问字符串的内容,请在使用前调整其大小:

string temp1;
//    VVVVVV
temp1.resize(3); // now it contains 3 elements

temp1[0]='a'; // set first element, ok
temp1[1]='b'; // set second element, ok
temp1[2]='c'; // set third element, ok

【讨论】:

【参考方案2】:

这里的代码有错误:

string temp1;

temp1[0]='a'; // Oops - past the end of the string!
temp1[1]='b'; // Oops - past the end of the string!
temp1[2]='c'; // Oops - past the end of the string!

在每个指示的行中,您都在字符串末尾后面写,这会导致未定义的行为。

如果你想将temp1设置为"abc",你可以试试

temp1 = "abc";

temp1 += 'a';
temp2 += 'b';
temp3 += 'c';

【讨论】:

谢谢!但是如果我打印字符串 temp1,我会得到正确的预期输出 'abc' 。如果它应该导致未定义的行为,为什么会发生这种情况? @adikj 未定义的行为意味着代码被破坏,代码可以做任何事情。仅仅因为它输出你所期望的并不意味着它没有被破坏。【参考方案3】:

这段代码:

string temp1;
temp1[0]='a';  // UB

调用未定义的行为。 temp1 的大小为 0,因此不允许在第一个位置(索引 0)建立索引(如 cmets 中所指出的,有一个例外是 写入 '\0' 处的字符 @987654324 @index 允许的)。

改为使用+=push_back 添加字符。或者在索引到它之前将字符串调整为适当的大小。

【讨论】:

谢谢!但是,如果我打印字符串 temp1,我会得到 'abc' 作为输出。如果不允许,为什么字符串有正确的值? UB 意味着任何事情都有可能发生。有时值可能看起来是正确的,但 整个 程序已损坏。 哦。感谢您的澄清! @cigien "temp1 的大小为 0,因此不允许在第一个位置(索引 0)建立索引" - 从技术上讲,在 C++11 及更高版本中,它 IS 允许写入index=size() 的位置,但唯一允许写入该位置的char 值是'\0',否则会发生UB。将任何char 值写入index&gt;size() 始终是UB。 @RemyLebeau 感谢您的更正,我很感激。编辑了答案。我似乎从来不记得那个例外:p

以上是关于使用 push_back 向向量添加非空字符串,向量内容为空。为啥字符串没有添加到向量中?的主要内容,如果未能解决你的问题,请参考以下文章

Flutter - 必须向 Text 小部件提供非空字符串

必须向 Text 小部件提供非空字符串 - 颤振

如何修复“必须向文本小部件提供非空字符串”。颤振错误?

必须向 Text 小部件 Flutter Api 提供非空字符串

必须向 Text 小部件提供非空字符串。错误显示,但 null-safety 不适用于代码

执行 push_back 后,集合的 C++ 向量给出分段错误