Fast temporary dynamic arrays? (And slicing of them)

Tom Kazimiers 2voodoo at gmx.de
Sun Sep 5 18:02:29 PDT 2010


Hi all,

so I have started to look at D and dug through the documentation, but
could not get a good answer on the following:

How can I have a (temporary) dynamic array on stack and make references
to it (no copying)? I successively put integers in an array (but don't
know how much there will be in advance) with an appender!(int[]) and get
the date out with appender.data(). Later on I pass the result to a
method as an "in int[]" parameter. Is that already a reference or will
it be copied? Are there better methods to accomplish this? The method
receiving such an array will not modifiy contents of the array, but only
read from it.

Thanks in advance,
Tom

--

P.s. To put a bit of context around that, here some notes on what I am
working (some questions here as well, but above is the primary one):

My first try-out project in D is an Object file reader (often used in
computer graphics). Part of that is a parsing method which parses a
single line that contains a definition of a face (a polygon). It could
for instance look like this:

f 1//10 2//10 3//10

That means it is a triangle face of points 1, 2 and 3 (three groups,
first number is point index). Furthermore no texture coordinate index
(no number between two slashes) and each with normal vector index 10.
But I don't want to go into detail of that. Say I want to parse that
line with D and in the end call a method to process that face with
references to lists of the different point indices:

void process_face(int index, int vcount, in int[] vertices,
                  in int[] texcoords = null, in int[] normals = null)
{
    ...
}

(I guess "in" means sth. like const reference)

The arrays should not be copied, but be references. The line parsing
method now has the following lines (line is a char[]):

//search face
int index = indexOf(line, "f ");
if(index != -1)
{
    line = line[index+2 .. $];  // slice away the "f " part
    fc++; // increment face count

    int slash;
    while(true)
    {
         slash = indexOf(line, " /");  // leading spaces + slashes?
         if(slash != -1)
             // remove space
             line = line[0 .. slash] ~ line[slash+1 .. $];
         else
             break;
    }
    while(true)
    {
        slash = indexOf(line, "/ ");  // trailing spaces + slashes?
            if(slash != -1)
                // remove space	
                line = line[0 .. slash+1] ~ line[slash+2 .. $];
            else
                break;
    }

    // dynamic vertex, texture and normal arrays
    auto vIndices = appender!(int[])();
    auto tIndices = appender!(int[])();
    auto nIndices = appender!(int[])();

    // some indices
    int vi,ti,ni;

    // split line on white spaces
    char[][] vertexCoords = split( line );
    // go through each part - are those splittings ok?
    foreach(char[] coord; vertexCoords) {
        vi = parse!(int)(coord); //get int from string
        vIndices.put( vi ); // save it in vertex array
        if (coord[0] == '/') { // follows a slash?
            coord = coord[1 ..$]; // get rid of it
            if (coord[0] == '/') { // follows another slash?
                coord = coord[1 ..$]; // get rid of it
                ni = parse!(int)( coord ); // git following int
                nIndices.put( ni ); // save it in normal array
            } else {
                ti = parse!(int)( coord );
                tIndices.put( ti );
                if (coord[0] == '/') {
                    coord = coord[1 ..$];
                    int ni = parse!(int)( coord );
                    nIndices.put( ni );
                }
            }
        }
    }

    // array references for passing to processing method
    int[] varray = null, tarray = null, narray = null;

    // if we have data, save it to appropriate varible
    if( !(vIndices.data().empty()) )
	    varray = vIndices.data();

    if( !(tIndices.data().empty()) )
	    tarray = tIndices.data();


    if( !(nIndices.data().empty()) )
	    narray = nIndices.data();

    // process it
    process_face(fc, vIndices.data().length, varray, tarray, narray);

    return;
}

I hope this rather lengthy explanation is no problem here (if looked on
it at all, since it was not my primary question :-) ). If you are in the
mood, please comment on how make parts on it better. It is pretty much
my first D code. Well, thanks.

Cheers
Tom


More information about the Digitalmars-d-learn mailing list