Base-packed reader cleanup.

git-svn-id: file:///humgen/gsa-scr1/gsa-engineering/svn_contents/trunk@1847 348d0f76-0448-11de-a6fe-93d51630548a
This commit is contained in:
hanna 2009-10-15 01:26:23 +00:00
parent 316b30ee56
commit 8dca236958
1 changed files with 36 additions and 19 deletions

View File

@ -5,6 +5,7 @@ import org.broadinstitute.sting.utils.StingException;
import java.io.*;
import java.nio.ByteOrder;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
/**
* Reads a packed version of the input stream.
@ -21,30 +22,45 @@ public class BasePackedInputStream<T> {
/**
* Ultimate source for packed bases.
*/
private final InputStream targetInputStream;
private final FileInputStream targetInputStream;
/**
* Channel source for packed bases.
*/
private final FileChannel targetInputChannel;
/**
* A fixed-size buffer for word-packed data.
*/
private final ByteBuffer buffer;
private final ByteOrder byteOrder;
/**
* How many bases are in a given packed word.
*/
private final int basesPerPackedWord = PackUtils.bitsInType(Integer.class)/PackUtils.BITS_PER_BASE;
/**
* How many bytes in an integer?
*/
private final int bytesPerInteger = PackUtils.bitsInType(Integer.class)/PackUtils.BITS_PER_BYTE;
public BasePackedInputStream( Class<T> type, File inputFile, ByteOrder byteOrder ) throws FileNotFoundException {
this(type,new BufferedInputStream(new FileInputStream(inputFile)),byteOrder);
this(type,new FileInputStream(inputFile),byteOrder);
}
public BasePackedInputStream( Class<T> type, InputStream inputStream, ByteOrder byteOrder ) {
public BasePackedInputStream( Class<T> type, FileInputStream inputStream, ByteOrder byteOrder ) {
if( type != Integer.class )
throw new StingException("Only bases packed into 32-bit words are currently supported by this input stream. Type specified: " + type.getName());
this.targetInputStream = inputStream;
this.type = type;
this.buffer = ByteBuffer.allocate(PackUtils.bitsInType(type)/ PackUtils.BITS_PER_BYTE).order(byteOrder);
this.targetInputStream = inputStream;
this.targetInputChannel = inputStream.getChannel();
this.byteOrder = byteOrder;
}
/**
* Read the entire contents of the input stream.
* @param bwt array into which bases should be read.
* @return a byte array of the given length.
* @throws IOException if an I/O error occurs.
*/
public void read(byte[] bwt) throws IOException {
@ -58,18 +74,19 @@ public class BasePackedInputStream<T> {
* @param length number of bases to read from the stream.
* @throws IOException if an I/O error occurs.
*/
public void read( byte[] bwt, int offset, int length ) throws IOException {
int packedWord = 0;
final int basesPerEntry = PackUtils.bitsInType(Integer.class)/PackUtils.BITS_PER_BASE;
for( int i = 0; i < length; i++ ) {
if( i % basesPerEntry == 0 ) {
buffer.rewind();
targetInputStream.read(buffer.array());
packedWord = buffer.getInt();
}
public void read(byte[] bwt, int offset, int length) throws IOException {
int bufferWidth = ((bwt.length+basesPerPackedWord-1)/basesPerPackedWord)*bytesPerInteger;
ByteBuffer buffer = ByteBuffer.allocate(bufferWidth).order(byteOrder);
targetInputChannel.read(buffer);
targetInputChannel.position(targetInputChannel.position()+buffer.remaining());
buffer.flip();
int position = basesPerEntry - i % basesPerEntry - 1;
bwt[i+offset] = PackUtils.unpackBase((byte)((packedWord >> position*PackUtils.BITS_PER_BASE) & 0x3));
int packedWord = 0;
int i = 0;
while(i < length) {
if(i % basesPerPackedWord == 0) packedWord = buffer.getInt();
int position = basesPerPackedWord - i%basesPerPackedWord - 1;
bwt[offset+i++] = PackUtils.unpackBase((byte)((packedWord >> position*PackUtils.BITS_PER_BASE) & 0x3));
}
}
}