Jump to page: 1 2
Thread overview
What's wrong with this code?
Jan 08, 2011
Sean Eskapp
Jan 08, 2011
Michal Minich
Jan 08, 2011
Tomek Sowiński
Re: What's wrong with this code? (OP)
Jan 08, 2011
Sean Eskapp
Jan 08, 2011
bearophile
Jan 08, 2011
Michal Minich
Jan 08, 2011
bearophile
Jan 11, 2011
Dmitry Olshansky
Jan 11, 2011
bearophile
Jan 11, 2011
spir
January 08, 2011
I had some code that was segfaulting, so I rewrote the basic idea as a fibonacci function, and lo and behold, it still segfaults. Why, and how to fix?
January 08, 2011
On Sat, 08 Jan 2011 20:34:39 +0000, Sean Eskapp wrote:

> 		if(left == null)

1) write if (left is null) instead if checking for null. Equality operator is rewritten to a.opEquals(b), which you don't want if you checking for null.

> this()
> {
>     left = right = null;
> }
2) default constructor as you written it is not needed, fields are always initialized to default value of their type, which is in this case null.

> private const Fib* left, right;
3) Classes in D are reference types. It should be
 private const Fib left, right;

4) second constructor - Classes in D are reference types, & operator is not needed (see point 3), parameter left and right are already references to class.
January 08, 2011
Sean Eskapp napisał(a):

> I had some code that was segfaulting, so I rewrote the basic idea as a
> fibonacci function, and lo and behold, it still segfaults. Why, and how to fix?

This looks fishy:

class Fib
{
	private const Fib* left, right;
...
	this(in Fib left, in Fib right)
	{
		this.left = &left;
		this.right = &right;
	}


Are you sure you want a pointer to class? Classes have reference semantics in D (like Java). Structs are value types, though. Anyway, it looks like the ctor takes the address of the reference placed on the stack.

-- 
Tomek
January 08, 2011
Sean Eskapp:

> I had some code that was segfaulting, so I rewrote the basic idea as a fibonacci function, and lo and behold, it still segfaults. Why, and how to fix?

Two versions:

struct Fib {
    private const Fib* left, right;

    this(in Fib* left=null, in Fib* right=null) {
        this.left = left;
        this.right = right;
    }

    const int evaluate() {
        if (left is null)
            return 1;
        else
            return left.evaluate() + right.evaluate();
    }
}

Fib* bar(int n) {
    if (n == 0 || n == 1)
        return new Fib();
    else
        return new Fib(bar(n - 1), bar(n - 2));
}

void main() {
    auto x = bar(5);
    assert(x.evaluate() == 8);
}

--------------------

struct Fib {
    private const Fib* left, right;

    this(in Fib* left=null, in Fib* right=null) {
        this.left = left;
        this.right = right;
    }

    const int evaluate() {
        if (left is null)
            return 1;
        else
            return left.evaluate() + right.evaluate();
    }
}

Fib* bar(int n) {
    if (n == 0 || n == 1)
        return new Fib();
    else
        return new Fib(bar(n - 1), bar(n - 2));
}

void main() {
    auto x = bar(5);
    assert(x.evaluate() == 8);
}

Bye,
bearophile
January 08, 2011
On Sat, 08 Jan 2011 16:39:34 -0500, bearophile wrote:

> Two versions:

Probably by mistake, both are the same.
January 08, 2011
Michal Minich:

> Probably by mistake, both are the same.

You are right, I am sorry :-)
In D the name of functions starts with lowercase.

class Fib {
    private const Fib left, right;

    this(in Fib left=null, in Fib right=null) {
        this.left = left;
        this.right = right;
    }

    const int evaluate() {
        if (left is null)
            return 1;
        else
            return left.evaluate() + right.evaluate();
    }
}

Fib bar(int n) {
    if (n == 0 || n == 1)
        return new Fib();
    else
        return new Fib(bar(n - 1), bar(n - 2));
}

void main() {
    auto x = bar(5);
    assert(x.evaluate() == 8);
}

Bye,
bearophile
January 08, 2011
Tomek got it right. Fixed by copying the objects, rather than using pointers. Thanks!
January 10, 2011
On Sat, 08 Jan 2011 15:46:01 -0500, Michal Minich <michal.minich@gmail.com> wrote:

> On Sat, 08 Jan 2011 20:34:39 +0000, Sean Eskapp wrote:
>
>> 		if(left == null)
>
> 1) write if (left is null) instead if checking for null. Equality
> operator is rewritten to a.opEquals(b), which you don't want if you
> checking for null.

Actually, this is no longer true.  For comparing two classes or interfaces, a == b becomes .opEquals(a, b)  which is defined in object.di and properly handles null references.

However, if checking for null, a is null is going to be more correct and as efficient as possible (a == b should be inlined to the same thing, but only if you have inlining enabled).

-Steve
January 11, 2011
On 09.01.2011 1:43, bearophile wrote:
> In D the name of functions starts with lowercase.
>
Or more precisely, in Phobos.
There is no such requirement in D,  I may suggest you stop using such a general and assertive posts, so not to confuse anyone.

-- 
Dmitry Olshansky

January 11, 2011
Dmitry Olshansky:

> Or more precisely, in Phobos.
> There is no such requirement in D,  I may suggest you stop using such a
> general and assertive posts, so not to confuse anyone.

Let's create ecosystem-wide name requirements for D code, then! :-) The Phobos ones may be a good starting point. This topic is neglected, it needs a much wider discussion.

Bye,
bearophile
« First   ‹ Prev
1 2