title: Dynamically allocated doubly linked circular list class instances segfault C++
body: <p>Using this template class works perfectly fine when main operates with <em>constructed</em> variables of type dlring, yet my goal is to allow <em>dynamic allocation</em>, so I can handle a non-predefined number of doubly linked circular lists to allow usage of such functions as:</p>
  
  <ul>
  <li>Splitting a list into two by either using a node position (via<br>
  iteration) or value entry.</li>
  <li>Same goes for linking two lists into one with a single head/tail
  pair.</li>
  <li>Node exporting from one list (instance) to another.</li>
  <li>Etc.</li>
  </ul>
  
  <p>I'm pretty much sure there is an elegant workaround which is simply not known by me yet, but I don't think it's nice to come up with a question for the community if you didn't struggle enough to resolve. (checked google </p>
  
  <p>So with that goals I'm supposed to dynamically allocate memory (via constructor calls) using some kind of pointer-to-pointer, AFAIK. If there is a smarter way to implement these, please let me know. My solution attempt is given in the end of this <em>snippet</em>. Feel free to criticize all of the below.</p>
  
  <h2><em>Doubly linked circular list class header (simplified)</em></h2>
  
  <pre><code>template &lt;typename T&gt;
  class dlring
  {
      struct node
      {
          T data;
          node* prev;
          node* next;
          node(T t, node* p, node* n) : data(t), prev(p), next(n) {}
      };
      node* head;
      node* tail;
  public:
      dlring():head(nullptr), tail(nullptr){}
      bool empty() const { return ( !head || !tail ); }
  //operator bool() const { return !empty(); }
      void Push(T);
      T pop_back();
      ~dlring()
      {
          while(head)
          {
              node* temp(head);
              head=head-&gt;next;
              delete temp;
          }
      }
  };
  </code></pre>
  
  <p>Should I use the commented out <em>operator bool</em> overload?    </p>
  
  <h2><em>pop_back and Push methods:</em></h2>
  
  <pre><code>template &lt;typename T&gt;
  void dlring&lt;T&gt;::Push(T data)
  {
      head = new node(data, tail, head); 
      if( head-&gt;next )
      {
          head-&gt;next-&gt;prev = head;
          tail-&gt;next = head;
      }
      if( empty() )
      {
          tail = head;
          head-&gt;next=tail;
          head-&gt;prev=tail;
          tail-&gt;next=head;
          tail-&gt;prev=head;
      }
  }
  template&lt;typename T&gt;
  T dlring&lt;T&gt;::pop_back()
  {
      if( empty() )
          std::cout&lt;&lt;"List empty";
      node* temp(tail);
      T data( tail-&gt;data );
      tail = tail-&gt;prev ;
      if (tail != temp)
      {
          tail-&gt;next-&gt;next = head; 
          head-&gt;prev = tail;
      }
      else
      {
          head = nullptr;
          tail = nullptr;
      }
      delete temp;
      temp = nullptr;
      return data;
  }
  </code></pre>
  
  <p>My attempt doesn't have the right behaviour: When I'm trying to show all the lists via a iteration the code fails, segfaulting on head->data access attempt of dlist[<em>0</em>], where <em>0</em> is an iteration of k. Here is the snippet:</p>
  
  <pre><code>   int main()
      {
      int k;
        std::cout&lt;&lt;"Rings count?"&lt;&lt;std::endl;
        std::cin&gt;&gt;k;
          dlring&lt;int&gt;* dlist = new dlring&lt;int&gt;[k]; //I suppose I'm allocating *k*
       //dlring&lt;int&gt; elements. this line is not confirmed to call the constructor.
      (dlist[0]).Push(10);
      (dlist[0]).Push(13);
      (dlist[1]).Push(99);
      /*{
      while(!dlist[0].empty())
      std::cout&lt;&lt;(dlist[0]).pop_back()&lt;&lt;" ";
      std::cout&lt;&lt;std::endl;
      while(!dlist[1].empty())
      std::cout&lt;&lt;(dlist[1]).pop_back()&lt;&lt;" ";
      }*/
      //this section works perfectly fine, while this
        for(int i=0;i&lt;k;i++)
        {
          while(!dlist[k].empty())
          std::cout&lt;&lt;(dlist[k]).pop_back()&lt;&lt;" ";
          std::cout&lt;&lt;std::endl;
        }
      //is causing a segmentation fault while attempting to access dlist[*0*].tail-&gt;data.
      std::cout&lt;&lt;(dlist[0]).head-&gt;data;
      //line was checked and is confirmed to be functional, 
      //I suppose dlist[variable] has some trick I don't know yet.
      //what I wish to look like an instance call would be *
      return 0;
      }
  </code></pre>
  
  <p>Best regards. Again, feel free to criticize <em>any</em> of my code/logics.</p>