简体   繁体   English

该程序如何运作

[英]How does this program work

This is my first C++ program. 这是我的第一个C ++程序。 It prints the number of words in the input. 它打印输入中的单词数。

My first question, how does it go into the loop and add to the count? 我的第一个问题是,它如何进入循环并增加计数? is it every time i type the space character? 每次输入空格字符都可以吗? if so, how does it know I'm trying to count words? 如果是这样,它怎么知道我要数单词?

using namespace std;

int main() {
    int count;
    string s;
    count = 0;
    while (cin >> s)
        count++;
    cout << count << '\n';
    return 0;
}

My second question. 我的第二个问题。 Can someone explain to me what namespace std means for a begineer? 有人可以向我解释std命名空间对初学者意味着什么吗?

When you do cin >> string. 当您执行cin >>字符串时。 You will read a word and put it in the string. 您将阅读一个单词并将其放入字符串中。 Yes, it will read char by char until reach the delimiter. 是的,它将逐字符读取char直到到达定界符。

Std means Standard. 标准表示标准。 Standard C++ library is inside the std namespace. 标准C ++库位于std名称空间内。 You can rewrite or code without the using namespace std : 您可以在不使用命名空间std的情况下进行重写或编码:

int main() {
    int count;
    std::string s;
    count = 0;
    while (std::cin >> s)
        count++;
    std::cout << count << '\n';
    return 0;
}

I discourage that novices use the using namespace std statement because it is harder to understand what is going on. 我不鼓励新手使用using名称空间std语句,因为这很难理解发生了什么。

In your code, cin >> s attempts to read a std::string from input stream. 在您的代码中, cin >> s尝试从输入流中读取std::string If the attempt succeeds, then the returned value of cin >> s implicitly converts into true and the while loop continues, incrementing the counter. 如果尝试成功,则cin >> s的返回值将隐式转换为true ,并且while循环继续进行,从而使计数器递增。 Otherwise, the while loop exits when the attempt fails, as there is no more data to read from the input stream. 否则,当尝试失败时,while循环将退出,因为没有更多数据可从输入流中读取。

You can use std::distance to count the words, as shown below: 您可以使用std::distance来计数单词,如下所示:

#include <iostream>
#include <algorithm>
#include <iterator>
#include <string>

int main() {
        std::istream_iterator<std::string> begin(std::cin), end;
        size_t count = std::distance(begin, end);
        std::cout << count << std::endl;        
        return 0;
}

Demo : http://www.ideone.com/Hldz3 演示: http : //www.ideone.com/Hldz3

In this code, you create two iterators begin and end , passing both to std::distance function. 在此代码中,您将创建两个迭代器beginend ,并将它们都传递给std::distance函数。 The function calculates the distance between begin and end . 该函数计算beginend之间的距离。 The distance is nothing but the number of strings in the input stream, because the iterator begin iterates over strings coming from the input stream, and end defines the end of the iterator where begin stops iterating. 距离不过是输入流中字符串的数目,因为迭代器begin对输入流中的字符串begin迭代,而end定义了迭代器在begin停止迭代的位置的结尾。 The reason why begin iterates over strings is because the template argument to std::istream_iterator is std::string : begin遍历字符串的原因是因为std::istream_iterator的模板参数是std::string

 std::istream_iterator<std::string> begin(std::cin), end;
                     //^^^^^^^^^^^

If you change this to char , then begin will iterator over char , which means the following program will count the number of characters in the input stream: 如果将其更改为char ,则begin将迭代char ,这意味着以下程序将计算输入流中的字符数:

#include <iostream>
#include <algorithm>
#include <iterator>

int main() {
        std::istream_iterator<char> begin(std::cin), end;
        size_t count = std::distance(begin, end);
        std::cout << count << std::endl;        
        return 0;
}

Demo : http://www.ideone.com/NH52y 演示: http : //www.ideone.com/NH52y

Similarly, you can do many cool things if you start using iterators from <iterator> header and generic functions from <algorithm> header. 同样,如果从<iterator>头开始使用迭代器,并且从<algorithm>头开始使用泛型函数,则可以做很多很酷的事情。

For example, let say we want to count the number of lines in the input stream. 例如,假设我们要计算输入流中的行数。 So what change would we make to the above program to get the job done? 那么,我们将对上述程序进行哪些更改以完成工作? The way we change std::string to char when we wanted to count characters, immediately suggests that now we need to change it to line so that we could iterate over line (instead of char ). 当我们想对字符计数时,我们将std::string更改为char的方式立即表明,现在我们需要将其更改为line以便可以遍历line (而不是char )。

As no line class exist in the Standard library, we've to define one ourselves, but the interesting thing is that we can keep it empty as shown below, with full working code: 由于标准库中不存在任何line类,因此我们必须自己定义一个, 但是有趣的是我们可以使用完整的工作代码将其保留为空 ,如下所示:

#include <iostream>
#include <algorithm>
#include <iterator>
#include <string>

struct line {};   //Interesting part!

std::istream& operator >>(std::istream & in, line &) 
{ 
   std::string s; 
   return std::getline(in, s);
}

int main() {
        std::istream_iterator<line> begin(std::cin), end;
        size_t count = std::distance(begin, end);
        std::cout << count << std::endl;        
        return 0;
}

Yes, along with line , you've to define operator>> for line as well. 是的,除了line ,还必须为line定义operator>> It is used by std::istream_terator<line> class. std::istream_terator<line>类使用。

Demo : http://www.ideone.com/iKPA6 演示: http : //www.ideone.com/iKPA6

  1. Cin will capture input until a space, yes. Cin将捕获输入,直到空格为止。 The specific style of loop you have will go until an End-Of-File (EOF) is found or until bad input is provided. 循环的特定样式将一直持续到找到文件结尾(EOF)或提供错误的输入为止。 That loop doesn't look like common C++ practice to me, but it's described here . 在我看来,该循环看起来并不像普通的C ++惯例,但在此处进行了描述。

2. namespace std is how you tell the compiler where to look to find the objects you're referencing in your code. 2. namespace std是告诉编译器在哪里寻找在代码中引用的对象的方式。 Because different objects are "inside" different namespaces, you either have to tell the compiler where they are specifically (aka std::cin) or tell it for convenience where an object you use will be in the future (with using namespace std ). 因为不同的对象位于不同的名称空间“内部”,所以您必须告诉编译器它们的具体位置(aka std :: cin),或者为了方便起见告诉它将来使用的对象在哪里( using namespace std )。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM