Blitz logo

Blitz Bugs :

From: Patrick Guio (patrick.guio_at_[hidden])
Date: 2004-09-16 03:27:40


Hi again,

I meant of course line 174 in blitz/array-impl.h...

    explicit Array(int length0,
        GeneralArrayStorage<N_rank> storage = GeneralArrayStorage<N_rank>())
        : storage_(storage)
    {
// add those to harmonise with resize() method ?
BZPRECONDITION(length0 > 0);
BZPRECONDITION(N_rank == 1);
        length_[0] = length0;
        setupStorage(0);
    }

Patrick

---------- Forwarded message ----------
Date: Thu, 16 Sep 2004 10:21:39 +0200 (MET DST)
From: Patrick Guio <patricg_at_[hidden]>
To: blitz-bugs_at_[hidden]
Subject: Re: [Blitz-bugs] Zero size arrays bug: begin() != end()

On Tue, 14 Sep 2004, N Smethurst wrote:

I am not sure what is the expected behaviour of a standard (STL style)
begin and end iterator for an object of dimension 0 but what I can say is
that resize(0) is not valid in blitz
You can check in blitz/array/resize.cc line 37 here there is a
precondition
BZPRECONDITION(length0 > 0);
so if you compile with BZ_DEBUG you will get an error.
Now there might be a need for a precondition in the construtor as well?
line 166 in blitz/array-impl.h?

    Array(GeneralArrayStorage<N_rank> storage = GeneralArrayStorage<N_rank>())
        : storage_(storage)
    {
        length_ = 0;
        stride_ = 0;
        zeroOffset_ = 0;
    }

What do you think Julian?

Cheers, Patrick

> Hello there
>
> I discovered a bug in Array. When an array is initialised to zero size, the
> begin() iterator does not equal the end() interator.
>
> For example:
> Array<float, 1> vec(0);
> Array<float, 1>::iterator begin = vec.begin();
> Array<float, 1>::iterator end = vec.end();
>
> cout << "begin == end : " << (begin == end) << endl;
> cout << "begin != end : " << (begin != end) << endl;
>
> This gives:
> begin == end : 0
> begin != end : 1
>
> However, when an array is created then resized, there is no bug:
> Array<float, 1> vec;
> vec.resize(0);
> Array<float, 1>::iterator begin = vec.begin();
> Array<float, 1>::iterator end = vec.end();
> cout << "begin == end : " << (begin == end) << endl;
> cout << "begin != end : " << (begin != end) << endl;
>
> This gives:
> begin == end : 1
> begin != end : 0
>
> The behaviour is the same with higher dimension arrays:
> Array<float, 2> mat(0, 0);
> // begin != end
> Array<float, 2>::iterator begin = mat.begin();
> Array<float, 2>::iterator end = mat.end();
>
> Array<float, 2> mat1;
> mat1.resize(0, 0);
> // begin1 == end1
> Array<float, 2>::iterator begin1 = mat1.begin();
> Array<float, 2>::iterator end1 = mat1.end();
>
> Regards
>
> Nicholas