www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Segmentation fault from using SList in a class?

reply "Tim K." <invalid webinterface.com> writes:
Hello!


background.
Hello World was working, so I figured that I should try something 
more complex: a template class and si I went with a simple stack.

Using dmd the code I wrote causes a segmentation fault and I am 
not sure why.

import std.stdio;
import std.container.slist;


class Stack(T)
{
     SList!(T) s;
     this() {}
     void push(T element)
     {
         s.insertFront(element);
     }
}

int main()
{
     Stack!(int) x;
     writeln("1");
     SList!(int) p;
     writeln("2");
     p.insertFront(42);
     writeln("3");
     x.push(42);
     writeln("4");
     return 0;
}


This program prints the following into the console:
% dmd test.d && ./test
1
2
3
zsh: segmentation fault  ./test


I do not understand why the normal SList works fine but the one 
inside the object doesn't. What am I overlooking?


Best regards,
Tim
Jun 06 2015
next sibling parent reply Manfred Nowak <svv1999 hotmail.com> writes:
Tim K. wrote:

      Stack!(int) x;
x is not initialized. `auto x= new Stack!(int);' will do. -manfred
Jun 06 2015
parent reply "Tim K." <invalid webinterface.com> writes:
On Saturday, 6 June 2015 at 10:10:15 UTC, Manfred Nowak wrote:
 x is not initialized.

 `auto x= new Stack!(int);'
 will do.
Thank you two. But that leads me to another question: Why do I need to initialize x with a "new Stack" but I don't need to initialize p with a "new SList"? Best regards, Tim
Jun 06 2015
next sibling parent reply "Marc =?UTF-8?B?U2Now7x0eiI=?= <schuetzm gmx.net> writes:
On Saturday, 6 June 2015 at 10:16:12 UTC, Tim K. wrote:
 On Saturday, 6 June 2015 at 10:10:15 UTC, Manfred Nowak wrote:
 x is not initialized.

 `auto x= new Stack!(int);'
 will do.
Thank you two. But that leads me to another question: Why do I need to initialize x with a "new Stack" but I don't need to initialize p with a "new SList"?
Because `SList` is a struct, which is a value type that is allocated where you declare it (here on the stack), while you used a class, which is a reference type and has to be allocated with `new`. You can also turn your `Stack` type into a struct, then it works, too. (You just need to remove the constructor, which is empty anyway.)
Jun 06 2015
parent "Tim K." <invalid webinterface.com> writes:
On Saturday, 6 June 2015 at 10:20:34 UTC, Marc Schütz wrote:

 Because `SList` is a struct, which is a value type that is 
 allocated where you declare it (here on the stack), while you 
 used a class, which is a reference type and has to be allocated 
 with `new`.

 You can also turn your `Stack` type into a struct, then it 
 works, too. (You just need to remove the constructor, which is 
 empty anyway.)
That makes sense. I overlooked that in SList's documentation and thought it was just a regular old class, too. Best regards, Tim
Jun 06 2015
prev sibling parent "Panke" <tobias pankrath.net> writes:
On Saturday, 6 June 2015 at 10:16:12 UTC, Tim K. wrote:
 On Saturday, 6 June 2015 at 10:10:15 UTC, Manfred Nowak wrote:
 x is not initialized.

 `auto x= new Stack!(int);'
 will do.
Thank you two. But that leads me to another question: Why do I need to initialize x with a "new Stack" but I don't need to initialize p with a "new SList"? Best regards, Tim
Best way to construct a std.container is to use std.container.make.
Jun 06 2015
prev sibling parent Jonathan M Davis via Digitalmars-d-learn writes:
On Saturday, June 06, 2015 09:44:36 Tim K. via Digitalmars-d-learn wrote:
 Hello!


 background.
 Hello World was working, so I figured that I should try something
 more complex: a template class and si I went with a simple stack.

 Using dmd the code I wrote causes a segmentation fault and I am
 not sure why.

 import std.stdio;
 import std.container.slist;


 class Stack(T)
 {
      SList!(T) s;
      this() {}
      void push(T element)
      {
          s.insertFront(element);
      }
 }

 int main()
 {
      Stack!(int) x;
      writeln("1");
      SList!(int) p;
      writeln("2");
      p.insertFront(42);
      writeln("3");
      x.push(42);
      writeln("4");
      return 0;
 }


 This program prints the following into the console:
 % dmd test.d && ./test
 1
 2
 3
 zsh: segmentation fault  ./test


 I do not understand why the normal SList works fine but the one
 inside the object doesn't. What am I overlooking?
From the looks of it, you never initialized x, so it's null. So, the problem
has nothing to do with SList. It's the fact that you're trying to dereference a null reference. You need to call new to allocate a Stack!int, not just declare a reference to one. void main() { Stack!int x x.push(42); } would have exactly the same problem. You need something like auto x = new Stack!int; - Jonathan M Davis
Jun 06 2015