
Leland Brown said: (by the date of Fri, 16 Jun 2006 14:14:31 -0700 (PDT))
--- Janek Kozicki <janek_listy@wp.pl> wrote:
One last note: above design does not allow to resize vectors and matrices in runtime. This limits the library usage. Should there be added a slower complementary library that will allow to resize data in runtime? Any ideas?
I agree this is useful, and also that it has a run-time penalty. But I have an idea to reduce that penalty, as well as reducing the work for the library implementer to add this feature, without having to write a whole parallel library. I had hoped to add this to my own matrix library, but I haven't yet. (Actually, I need this capability, but I'm using a less efficient workaround for now.)
heh, perhaps you can help writing it here in boost, and then use it in your program ;) <snip>
A compromise that works in many situations is to set a maximum size for each object at compile-time, allocate memory for the maximum size, and then only use part of the structure depending on its current size set at run-time. This allows the data and its operations to have an adjustable size (up to a predetermined maximum) while avoiding heap allocation - the best of both worlds. As an example of how this can be implemented, suppose we augment our vector template with an extra template argument of type bool, which tells if the vector is resizable - e.g.:
vector<3,double,false> // 3D vector of double
where the last argument defaults to false, so it doesn't need to be specified always.
vector<5,double,true> // vector *up to* 5D
The resizable vector needs an extra member to store the actual current size, and that size should be used as the upper limit in loops, instead of the size in the template argument (see example below).
Both kinds of vectors can be implemented with one definition, by inheriting from separately specialized base classes. Here's an example:
<snip, interesting stuff>
FWIW, I'm not happy with the syntax above of adding an extra bool parameter. For my code, I planned to use a negative value of N to indicate resizable:
vector<3,double> // fixed 3D vector vector<-5,double> // up to 5D vector matrix<4,-14,double> // 4x1 to 4x14 matrix matrix<-14,4,double> // 1x4 to 14x4 matrix matrix<-6,-6,double> // both values resizable
but this is admittedly nonintuitive (though it does make both the library and user code more concise).
that is a very intersting idea. Especially because matrices would require two bools. If stated out clearly in the documentation, perhaps we could use it? What others think?
BTW, this is where I'd really like to see templatized typedefs in C++, allowing us to define:
template< int N, type T > typedef vector< N, T, false > fixed_vector;
template< int N, type T > typedef vector< N, T, true > resizable_vector;
Thus we'd have:
fixed_vector<N,T> resizable_vector<N,T>
while using the common vector template defined above.
uh, wait. It's not possible currently? I'm not 100% sure but I think that I was using similar code some time in the past...
In _The Design and Evolution of C++_, Bjarne Stroustrup says adding templatized typedefs would be a "technically trivial" extension, but questions the wisdom of the idea. Perhaps there's been some discussion about this topic in Boost?
At the end I want again to recall my "table of" .. err " concepts"? Because resizable_vector really niecely fits here, so that we can see more similarities in the design. everything determined| something determined | everything determined during compilation | during compile time | during runtime stage | sth during runtime | ---------------------+----------------------+------------------ t1_quantity | t2_quantity | t3_quantity fixed_quantity | scalable_quantity | free_quantity | | vector<3> | resizable_vector | vector.resize(3) matrix<4,4> | resizable_matrix | matrix.resize(4,4) fixed_vector ? | | free_vector ? -- Janek Kozicki |