Handling a BigWig file from Java+JNI : my notebook
In a previous post I've shown how to use a Java JNI interface to control a NCURSES panel from a java program.
I'll show here how to use java JNI to call the C methods developped by Jim Kent's team at UCSC to handle a BigWig file.
The Makefile for compiling the following sources is defined below:
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
JAVA_HOME=/path/to/jdk | |
JKENTSRC=path/to/jkentsrc | |
CFLAGS= -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -I ${JKENTSRC}/src/inc -I ${JAVA_HOME}/include -I ${JAVA_HOME}/include/linux | |
JAVACC=javacc | |
test:libbigwig.so | |
java BigWig wgEncodeCrgMapabilityAlign100mer.bigWig | |
libbigwig.so:BigWig.h BigWig.c | |
gcc ${CFLAGS} -fpic -c BigWig.c -o BigWig.o | |
gcc -shared -o $@ BigWig.o ${JKENTSRC}/src/lib/jkent/jkweb.a -lm -lz | |
BigWig.h:BigWig.java | |
${JAVA_HOME}/bin/javac BigWig.java | |
${JAVA_HOME}/bin/javah BigWig | |
Export the LD_LIBRARY_PATH:
export LD_LIBRARY_PATH=/path/to/current/directory
Download Jim Kent's sources from http://hgdownload.cse.ucsc.edu/admin/jksrc.zip. See the README file to compile jksrc/lib and jksrc/jkOwnLib.
The java source BigWig.java declares seven natives JNI methods. They will call the C methods for opening and closing the bigWig file, and getting the summaries in a given genomic range.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import java.io.*; | |
public class BigWig | |
{ | |
private long fd=0L; | |
/** open the bigWig file */ | |
private native long open(String fname); | |
/** close the big wig file */ | |
private native void close(long fid); | |
/** get the summaries in the given genomic range */ | |
private native Double mean(long fid,String chrom,int start,int end); | |
private native Double max(long fid,String chrom,int start,int end); | |
private native Double min(long fid,String chrom,int start,int end); | |
private native Double coverage(long fid,String chrom,int start,int end); | |
private native Double stddev(long fid,String chrom,int start,int end); | |
public BigWig(File f) throws IOException | |
{ | |
if(!f.exists()) throw new FileNotFoundException(f.toString()); | |
this.fd = open(f.getAbsolutePath()); | |
if(this.fd==0L) throw new IOException("Cannot open bigwig "+f); | |
} | |
@Override | |
protected void finalize() throws Throwable { | |
try { | |
close(); | |
} finally { | |
super.finalize(); | |
} | |
} | |
public Double getMean(String chrom,int start,int end) | |
{ | |
if(fd==0L) return null; | |
return mean(fd,chrom,start,end); | |
} | |
public Double getMax(String chrom,int start,int end) | |
{ | |
if(fd==0L) return null; | |
return max(fd,chrom,start,end); | |
} | |
public Double getMin(String chrom,int start,int end) | |
{ | |
if(fd==0L) return null; | |
return min(fd,chrom,start,end); | |
} | |
public Double getCoverage(String chrom,int start,int end) | |
{ | |
if(fd==0L) return null; | |
return coverage(fd,chrom,start,end); | |
} | |
public Double getStdDev(String chrom,int start,int end) | |
{ | |
if(fd==0L) return null; | |
return stddev(fd,chrom,start,end); | |
} | |
public void close() | |
{ | |
if(this.fd!=0L) | |
{ | |
close(this.fd); | |
} | |
this.fd=0L; | |
} | |
public static void main(String args[]) throws IOException | |
{ | |
System.loadLibrary("bigwig"); | |
BigWig big=new BigWig(new File(args[0])); | |
System.err.println(big.getMean("chr1",0,1000000)); | |
System.err.println(big.getMax("chr1",0,1000000)); | |
System.err.println(big.getMin("chr1",0,1000000)); | |
System.err.println(big.getCoverage("chr1",0,1000000)); | |
System.err.println(big.getStdDev("chr1",0,1000000)); | |
System.err.println(big.getMean("chr2",0,1000000)); | |
System.err.println(big.getMean("chr1",0,10)); | |
big.close(); | |
} | |
} |
After compiling the java source, the following C header is generated with javah:
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* DO NOT EDIT THIS FILE - it is machine generated */ | |
#include <jni.h> | |
/* Header for class BigWig */ | |
#ifndef _Included_BigWig | |
#define _Included_BigWig | |
#ifdef __cplusplus | |
extern "C" { | |
#endif | |
/* | |
* Class: BigWig | |
* Method: open | |
* Signature: (Ljava/lang/String;)J | |
*/ | |
JNIEXPORT jlong JNICALL Java_BigWig_open | |
(JNIEnv *, jobject, jstring); | |
/* | |
* Class: BigWig | |
* Method: close | |
* Signature: (J)V | |
*/ | |
JNIEXPORT void JNICALL Java_BigWig_close | |
(JNIEnv *, jobject, jlong); | |
/* | |
* Class: BigWig | |
* Method: mean | |
* Signature: (JLjava/lang/String;II)Ljava/lang/Double; | |
*/ | |
JNIEXPORT jobject JNICALL Java_BigWig_mean | |
(JNIEnv *, jobject, jlong, jstring, jint, jint); | |
/* | |
* Class: BigWig | |
* Method: max | |
* Signature: (JLjava/lang/String;II)Ljava/lang/Double; | |
*/ | |
JNIEXPORT jobject JNICALL Java_BigWig_max | |
(JNIEnv *, jobject, jlong, jstring, jint, jint); | |
/* | |
* Class: BigWig | |
* Method: min | |
* Signature: (JLjava/lang/String;II)Ljava/lang/Double; | |
*/ | |
JNIEXPORT jobject JNICALL Java_BigWig_min | |
(JNIEnv *, jobject, jlong, jstring, jint, jint); | |
/* | |
* Class: BigWig | |
* Method: coverage | |
* Signature: (JLjava/lang/String;II)Ljava/lang/Double; | |
*/ | |
JNIEXPORT jobject JNICALL Java_BigWig_coverage | |
(JNIEnv *, jobject, jlong, jstring, jint, jint); | |
/* | |
* Class: BigWig | |
* Method: stddev | |
* Signature: (JLjava/lang/String;II)Ljava/lang/Double; | |
*/ | |
JNIEXPORT jobject JNICALL Java_BigWig_stddev | |
(JNIEnv *, jobject, jlong, jstring, jint, jint); | |
#ifdef __cplusplus | |
} | |
#endif | |
#endif |
The C source implements the native methods defined in the java source. The code was inspired from ${JKENTSRC}/src/utils/bigWigSummary/bigWigSummary.c.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include "BigWig.h" | |
#include "common.h" | |
#include "linefile.h" | |
#include "hash.h" | |
#include "options.h" | |
#include "sqlNum.h" | |
#include "udc.h" | |
#include "bigWig.h" | |
JNIEXPORT jlong JNICALL Java_BigWig_open | |
(JNIEnv *env, jobject o, jstring s) | |
{ | |
const jbyte *fname = (*env)->GetStringUTFChars(env, s, NULL); | |
if(fname==NULL) return 0L; | |
struct bbiFile *bwf = bigWigFileOpen((char*)fname); | |
(*env)->ReleaseStringUTFChars(env, s, fname); | |
return (long)(bwf); | |
} | |
static jobject Java_BigWigSummary | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end,enum bbiSummaryType type) | |
{ | |
jobject ret=NULL; | |
jbyte *reference ; | |
struct bbiFile *bwf =(struct bbiFile*)ptr; | |
double nan0 = strtod("NaN", NULL); | |
double summaryValues[]={nan0}; | |
if(bwf==NULL) return NULL; | |
if(chrom==NULL) return NULL; | |
reference =(jbyte*) (*env)->GetStringUTFChars(env, chrom, NULL); | |
if(reference==NULL) return NULL; | |
if (bigWigSummaryArray(bwf, (char*)reference, start, end, type, 1, summaryValues)) | |
{ | |
if(!isnan(summaryValues[0])) | |
{ | |
jclass clazz = (*env)->FindClass(env, "java/lang/Double"); | |
jmethodID constructor = (*env)->GetMethodID(env,clazz, "<init>", "(D)V"); | |
ret= (*env)->NewObject(env,clazz, constructor,(jdouble)summaryValues[0]); | |
} | |
} | |
(*env)->ReleaseStringUTFChars(env, chrom, reference); | |
return ret; | |
} | |
JNIEXPORT jobject JNICALL Java_BigWig_mean | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end) | |
{ | |
return Java_BigWigSummary(env,o,ptr,chrom,start,end,bbiSumMean); | |
} | |
JNIEXPORT jobject JNICALL Java_BigWig_min | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end) | |
{ | |
return Java_BigWigSummary(env,o,ptr,chrom,start,end,bbiSumMax); | |
} | |
JNIEXPORT jobject JNICALL Java_BigWig_max | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end) | |
{ | |
return Java_BigWigSummary(env,o,ptr,chrom,start,end,bbiSumMin); | |
} | |
JNIEXPORT jobject JNICALL Java_BigWig_coverage | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end) | |
{ | |
return Java_BigWigSummary(env,o,ptr,chrom,start,end,bbiSumCoverage); | |
} | |
JNIEXPORT jobject JNICALL Java_BigWig_stddev | |
(JNIEnv *env, jobject o, jlong ptr, jstring chrom, jint start, jint end) | |
{ | |
return Java_BigWigSummary(env,o,ptr,chrom,start,end,bbiSumStandardDeviation); | |
} | |
JNIEXPORT void JNICALL Java_BigWig_close | |
(JNIEnv *env, jobject o, jlong ptr) | |
{ | |
struct bbiFile *bwf =(struct bbiFile*)ptr; | |
if(bwf==NULL) return; | |
bigWigFileClose(&bwf); | |
} |
Download a bigwig file for a test: http://hgdownload.cse.ucsc.edu/goldenPath/hg19/encodeDCC/wgEncodeMapability/wgEncodeCrgMapabilityAlign100mer.bigWig.
The main method in BigWig.java contains.a test:
java BigWig wgEncodeCrgMapabilityAlign100mer.bigWig
0.394749239542279
0.394749239542279
And here is the original output of the utility 'bigWigSummary':
bigWigSummary wgEncodeCrgMapabilityAlign100mer.bigWig -type=mean chr1 1 1000000 1
0.394749
0.394749
That's it,
Piere
No comments:
Post a Comment