Home > Enterprise >  How do I check if the program cout is empty?
How do I check if the program cout is empty?

Time:05-01

I am facing a problem where I have a void function which prints out AVL tree node values using inorder traversal. However, I also need to print out "EMPTY" if the void function does not have any cout.
And since the void function is recursive so I assume the cout << "EMPTY" << endl; can not be inside the function (Actually I tried but a lot of unncessary EMPTY were produced).
My question is that is there any way I can check the program/function cout, something like: if(cout is empty){ print "EMPTY" }

void inorder(node* n){
    if(n != NULL){
        inorder(n->left);
        cout << n->value << ' ';
        inorder(n->right);
    }
}

CodePudding user response:

You can't query cout to find out whether it printed something or not. There actually is a method (tellp()) that returns the position of a std::basic_ostream stream (which is what cout is), but when called on cout is always returns -1, presumably because cout is not keeping track of the number of characters it has printed (aka its "position" within the output stream).

Therefore the only practical way to know if something was printed is to instrument your inorder() function to provide that information to the caller, via a return-value (as Retired Ninja suggests in the comments) or via some other mechanism (e.g. writing to a by-reference argument, or setting a global variable, or etc)

CodePudding user response:

When you call inorder, it is guaranteed to produce some ouput if, and only if, its parameter is not NULL. So you can do this:

 void inorderTraverse(node* n)
 {
     if (n == NULL)
         std::cout << "EMPTY" << std::endl;
     else
         inorder(n);
 }

Then, wherever you first call inorder, call inorderTraverse instead.

CodePudding user response:

The way to do this is to have two functions:

  • one that the user calls, and which will print “EMPTY” if the tree is empty
  • one that does everything else

The common way to do this is with a “detail” namespace, but any other method for having a helper function would work as well:

namespace detail{
    void inorder(node* n){
        if(n != NULL){
            inorder(n->left);
            std::cout << n->value << ' ';
            inorder(n->right);
        }
    }
}

void inorder(node* n){
    if(n) detail::inorder(n);
    else std::cout << "EMPTY";
}

Another common way of doing this is having an additional, defaulted-argument (boolean, in this case) to indicate whether or not it is a toplevel invocation:

void inorder(node* n, bool is_top=true){
    if (n != NULL){
        inorder(n->left, false);
        std::cout << n->value << ' ';
        inorder(n->right, false);
    }else if(is_top){
        std::cout << "EMPTY";
    }
}

I personally do not like flaggy code, though — the helper function is an old, recognizable idiom and avoids the overhead of the boolean tests at every leaf node.

  • Related