2

I'm getting hard time figuring out solution for calling constructor of class which uses templates.

--Header file

template <class Item>
class Binary_tree
{
    string file_name;
    list<Item> arr_data;
public:
    Binary_tree(string fname);
    void printArr();
};

--cpp file

template <typename Item>
Binary_tree<Item>::Binary_tree(string fname)
{
    File_Name = fname;
    total = 0;
    root = nullptr;

    std::ifstream filestream(fname);
    string line;

    while (!filestream.eof())
    {
        filestream >> line;
        arr_data.push_back(line);
    }
}

template <typename Item>
void Binary_tree<Item>::printArr()
{
    int size = arr_data.size();

    for (int i = 0; i < size; i++)
    {
        cout << "arr_data [" << i << "] is: " << arr_data[i] << endl;
    }
} 

--main.cpp

int main(int argc, char** argv)
{
 Binary_tree<string> test(file); 
 test.printArr();

 return 0;
}

Right now I'm getting LNK1120 and LNK2019 errors.

Gaurav
  • 31
  • 1
  • 5

2 Answers2

4

Note: this answer answers the original question which was replaced by an entirely different qestion!

The declaration is for a function as is described at the Most Vexing Parse:

Binary_tree<string> test(Binary_tree<string>(file));

This declares a function named test() returning a Binary_tree<string> and taking an argument or type Binary_tree<string> named file. Here are variations for fixing the problem:

Binary_tree<string> test0(file);
Binary_tree<string> test1 = Binary_tree<string>(file);
Binary_tree<string> test2{Binary_tree<string>(file)};
Dietmar Kühl
  • 150,225
  • 13
  • 225
  • 380
  • I tried all of them, and keep getting following 4 LNK errors. LNK2019 and LNK1120 – Gaurav Jul 12 '15 at 00:29
  • @Gaurav: sure. You need to define the function templates and I guess you do so in a separate .cpp file (you don't show the code to I need to use my clairvoyance which isn't entirely reliable). If you put the definition of function templates into a .cpp file you'll need to explicitly instantiate them (there are plenty questions and answers on this topic) of see my [blog](http://kuhllib.com/2012/01/22/source-organization-of-templates/). The easiest approach is to put the definition of the function templates into the header to have the compiler implicitly instantiate them. – Dietmar Kühl Jul 12 '15 at 00:35
  • I looked at your page, and I know the concept and mostly I'm implementing it as you showed as well. If you want to see my code then here it is: '#include "BinaryTree.h" template Binary_tree::Binary_tree(string fname) { File_Name = fname; total = 0; root = nullptr; std::ifstream filestream(fname); string line; while (!filestream.eof()) { filestream >> line; arr_data.push_back(line); } } int main() { string file = "HeapQuestions.txt"; Binary_tree test(file);// = (Binary_tree(file)); test.printArr(); return 0; }' – Gaurav Jul 12 '15 at 00:46
  • @Gaurav: so you have your template definitions in a .cpp which is probably **not** what you want! Put the code into `BinaryTree.h` and it should compile. Whether it would work I don't know. I spotted the use of `.eof()` in your code which is certainly wrong! You need to check *after* reading, e.g., using `while (filestream >> line) { ... }` (which wouldn't read a line but rather just one word; if you want to read a line you'd use `std::getline(filestream, line)`). Not that you should **not** paste code into comment, either! You'd rather update your question... – Dietmar Kühl Jul 12 '15 at 00:59
  • `#include "BinaryTree.h" template Binary_tree::Binary_tree(string fname) { File_Name = fname; total = 0; root = nullptr; std::ifstream filestream(fname); string line; while (!filestream.eof()) { filestream >> line; arr_data.push_back(line); } } int main() { string file = "HeapQuestions.txt"; Binary_tree test(file);// = (Binary_tree(file)); test.printArr(); return 0; }` – Gaurav Jul 12 '15 at 00:59
  • I have c++ file structure right.. I used header files and cpp files. Also, I have checked that reading file is right as well. – Gaurav Jul 12 '15 at 01:04
  • Clearly, the link errors are unrelated to the original question: create a new question for the link error and post a minimal example showing the problem there (make sure it isn't a duplicate of the many questions of people who use the same incorrect placement of template code as you do, though: despite you telling me that your got the file structure right, I can tell you that you don't: read the blog article I posted above until you understand it...). – Dietmar Kühl Jul 12 '15 at 01:10
0

You've encountered the most vexing parse.

Binary_tree<string> test(Binary_tree<string>(file));

This is a function declaration, just like

Binary_tree<string> test(Binary_tree<string> file);

... which declares a function named test, which accepts a Binary_tree<string> as it's parameter, and returns a Binary_tree<string>.

cpplearner
  • 13,776
  • 2
  • 47
  • 72
  • I want to create an Binary_tree object which I can use later to call it's methods. Right now I'm unable to call printArr function. I keep getting errors like: Expression must have class type. – Gaurav Jul 12 '15 at 00:24