C++ out-of-line definition

2.9k Views Asked by At

I'm making a hash table and my class HashTable consists of the following struct and the following function in my header file:

class HashT
{
public:
  struct Node
  {
    std::string key;
    std::string value;
    Node* next;
  };

  Node** HashTArray;      

  void HashTCopy(struct Node** h1, struct Node** h2, unsigned int sz);

  HashT(const HashT& hm); (copy constructor that calls HashTCopy)

  unsigned int initialBucketCount = 10;
 };

In my source file, I define the function as such and used it in my copy constructor:

void HashT::HashTCopy(struct Node** h1, Node** h2, unsigned int sz)
{
  ...
}  

HashT::HashT(const HashT& hm)
{
new_HashT = new Node* [hm.initialBucketCount]; 
HashTCopy(new_HashT, hm.HashTArray, hm.initialBucketCount)
}

When I try to compile this I get an error saying out-of-line definition HashT::HashTCopy..." and.... note: type of 1st parameter of member declaration does not match definition. 'struct Node**' aka 'HashMap::Node** vs 'struct Node** aka HashMap::Node**'. The compiler points to struct... 'void HashTCopy(struct Node** h1,....)`. I can't seem to figure out the problem. My declaration and definition match up so what is the issue here? Thanks

4

There are 4 best solutions below

3
On
HashT.h:

#ifndef HASHT_H
#define HASHT_H

#include <iostream>

class HashT
{
public:
  struct Node
  {
    std::string key;
    std::string value;
    Node* next;
  };

  Node** HashTArray;      

  void HashTCopy(struct Node** h1, struct Node** h2, unsigned int sz);

  HashT(const HashT& hm);

  unsigned int initialBucketCount = 10;
 };

#endif

HashT.cpp:

#include "HashT.h"

void HashT::HashTCopy(struct Node** h1, Node** h2, unsigned int sz)
{
  //...
}  

HashT::HashT(const HashT& hm)
{
    Node** new_HashT = new Node* [hm.initialBucketCount]; 
    HashTCopy(new_HashT, hm.HashTArray, hm.initialBucketCount);
}
1
On

In the implementation, remove the struct before Node, i.e. change:

void HashT::HashTCopy(struct Node** h1, Node** h2, unsigned int sz)

to

void HashT::HashTCopy(Node** h1, Node** h2, unsigned int sz)

You don't need to write struct before variables of struct type in C++ (that's a C thing, and an outdated C thing at that). Your doing so here is confusing the compiler about what scope the name Node should appear in.

The Node struct is defined within the HashT class's namespace, so its full name is HashT::Node. Normally, types in a member function's argument list can be implicitly resolved within the class' namespace, without having to write HashT:: in front of them. But the redundant struct here seems to be throwing it off, and making it think that you're talking about some other Node struct outside of the HashT class, which it can't find a definition for, and which doesn't match the class declaration.

I'm not sure what the standard says about this, so the compiler may actually be in error here, but I'd bet that removing the struct will fix it.

0
On

i had such problem in one of my QT project i resolved it by moving strut definition to top in header file

so try something like this by updating header filer to.

  struct Node
  {
    std::string key;
    std::string value;
    Node* next;
  };

class HashT
{
public:
  Node** HashTArray;      

  void HashTCopy(struct Node** h1, struct Node** h2, unsigned int sz);

  HashT(const HashT& hm); (copy constructor that calls HashTCopy)

  unsigned int initialBucketCount = 10;
 };
1
On

Make the following changes:

class HashT
{
public:
  struct Node
  {
    std::string key;
    std::string value;
    Node* next;
  };

  Node** HashTArray;      

  static void HashTCopy(Node** h1, Node** h2, unsigned int sz);

  HashT(const HashT& hm); (copy constructor that calls HashTCopy)

  unsigned int initialBucketCount = 10;
 };
void HashT::HashTCopy(HashT::Node** h1, HashT::Node** h2, unsigned int sz)
{
  ...
}  

HashT::HashT(const HashT& hm)
{
new_HashT = new HashT::Node* [hm.initialBucketCount]; 
HashT::HashTCopy(new_HashT, hm.HashTArray, hm.initialBucketCount)
}

I think that the error is from the compiler not knowing exactly from where to get the Node structure, which is in the class HashT, so that by specifying the namespace (the class) in which the struct resides, will solve the provlem,