Download Reference Manual
The Developer's Library for D
About Wiki Forums Source Search Contact

java.nio.ByteBuffer to tango.io.Buffer Please help

Moderators: larsivi kris

Posted: 05/23/08 12:15:55 Modified: 05/23/08 13:08:56

Hello. it's about a relational algebra language DBMS I am going to port from C++/Java. Simply said my problem is to put and get (in Java terminology) data into buffer at a certain place.

Please see the Questions (UPPERCASE) in the following Java (draft) code :

// Java code
package suneido;
import java.nio.ByteBuffer;

/**
 * Used by database to store field values.
 * Provides a "view" onto a ByteBuffer.
 * <p>Format is:<br>
 * - one byte type = 'c', 's', 'l'<br>
 * - short n = number of fields<br>
 * - size (also referenced as offset[-1])<br>
 * - array of offsets<br>
 * size and array elements are of the type 
 * 
 * @author Andrew McKinlay
 *
 */
public class Record {
	class Type {
		final static byte BYTE = 'c';
		final static byte SHORT = 's';
		final static byte INT = 'l';
	}
	class Offset {
		final static int TYPE = 0;		// byte
		final static int NFIELDS = 1;	// short
		final static int SIZE = 3;		// byte, short, or int <= type
	};
	
	ByteBuffer buf;
	Rep rep;
	
	Record(int sz) {
		buf = ByteBuffer.allocate(sz);
		if (sz < 0x100)
			setType(Type.BYTE);
		else if (sz < 0x10000)
			setType(Type.SHORT);
		else
			setType(Type.INT);
		init();
	}
	private void init() {
		switch (getType()) {
		case Type.BYTE : rep = new ByteRep();
		case Type.SHORT : rep = new ShortRep();
		case Type.INT : rep = new IntRep();
		}
	}
	
	void add(byte[] data) {
		int n = getNfields();
		int offset = rep.getOffset(n - 1) + data.length;
		rep.setOffset(n++, offset);
		buf.position(offset);  


                // HOW DO I SET THE POSITION ??
                // DO I HAVE TO SET THE buffer.index PROPERTY 


		buf.put(data);
	}
	ByteBuffer get(int i) {
		if (i >= getNfields())
			return ByteBuffer.allocate(0);
		int start = rep.getOffset(i);
		buf.position(start);
		ByteBuffer result = buf.slice();
		int end = rep.getOffset(i - 1);
		result.limit(end - start);
		return result;
	}
	
	void setType(byte t) {
		buf.put(Offset.TYPE, t);
	}
	byte getType() {
		return buf.get(Offset.TYPE);



                // DO I HAVE TO USE : buffer.data[Offset.TYPE]



	}
	void setNfields(short nfields) {
		buf.putShort(Offset.NFIELDS, nfields);
	}
	short getNfields() {
		return buf.getShort(Offset.NFIELDS);
	}
	void setSize(int sz) {
		rep.setOffset(-1, sz);
	}
	int getSize() {
		return rep.getOffset(-1);
	}
	
	
	abstract class Rep {
		abstract void setOffset(int i, int offset);
		abstract int getOffset(int i);
	}
	class ByteRep extends Rep {
		void setOffset(int i, int sz) {
			buf.put(Offset.SIZE + i + 1, (byte) sz);
		}
		int getOffset(int i) {
			return buf.get(Offset.SIZE + i + 1);
		}
	}
	class ShortRep extends Rep {
		void setOffset(int i, int sz) {
			buf.putShort(Offset.SIZE + 2 * (i + 1), (short) sz);
		}
		int getOffset(int i) {
			return buf.getShort(Offset.SIZE + 2 * (i + 1));
		}
	}
	class IntRep extends Rep {
		void setOffset(int i, int sz) {
			buf.putInt(Offset.SIZE + 4 * (i + 1), sz);
		}
		int getOffset(int i) {
			return buf.getInt(Offset.SIZE + 4 * (i + 1));
		}
	}
}
// D programming language 

import tango.io.Buffer;
import tango.io.protocol.Reader;
import tango.io.protocol.Writer;

class Record {
 // enum stuff Type and Offset
// ie enum Offset {TYPE = 0, NFIELDS = 1, SIZE = 3};
	this(uint sz) 
        {
		buf = new Buffer(sz);
		if (sz < 0x100)
			setType(Type.BYTE);
		else if (sz < 0x10000)
			setType(Type.SHORT);
		else
			setType(Type.INT);
		init();
          }
  private :
	Buffer buf;
	Rep rep;


         // NOW HOW DO I IMPLEMENT put(index, data) AS WELL AS get(index)  AS SHOWN IN THE JAVA CODE
         //

}

Well, as you can see the problem is to get and put data at position().

Help is more than welcome. Bjoern

Author Message

Posted: 05/23/08 20:56:45

I haven't analyzed your problem fully, but it seems like you should be able to use a MappedBuffer and use seek to set the position prior to writing.

Posted: 05/23/08 21:34:03

Thanks larsivi (IceBear? :) ) I thought that too. But the MappedBuffer? constructor ...

this (FileConduit? host)

{

super (0); // very bad

requires a FileConduit?.

OKay. I think in my previous msg. I've used TOO much code. Let me reduce the code in order to explain what I really need. Due to the fact that I am not able to use : tango.io.protocol.put( 2, /+ the void[] index +/ aValue) I am at a stand still. However, I'll reduce the lines of code (tomorrow, sorry I am tiered) but I am still pretty optimistic that we'll find a solution. Thanks. hope to cu tomorrow. Bjoern