@ -1,4 +1,4 @@
// ReferenceContainerArray .java
// IODespatcher .java
// (C) 2009 by Michael Peter Christen; mc@yacy.net, Frankfurt a. M., Germany
// first published 20.03.2009 on http://yacy.net
//
@ -29,15 +29,9 @@ import java.io.IOException;
import java.util.concurrent.ArrayBlockingQueue ;
import de.anomic.kelondro.blob.BLOBArray ;
import de.anomic.kelondro.blob.HeapWriter ;
import de.anomic.kelondro.index.Row ;
import de.anomic.kelondro.order.ByteOrder ;
import de.anomic.kelondro.order.CloneableIterator ;
import de.anomic.kelondro.text.ReferenceContainerCache.blobFileEntries ;
import de.anomic.kelondro.util.FileUtils ;
/ * *
* merger class for files from ReferenceContainerArray .
* this is a concurrent merger that can merge single files that are queued for merging .
* when several ReferenceContainerArray classes host their ReferenceContainer file arrays ,
* they may share a single ReferenceContainerMerger object which does the sharing for all
@ -104,7 +98,7 @@ public class IODispatcher extends Thread {
public synchronized void merge ( File f1 , File f2 , BLOBArray array , Row payloadrow , File newFile ) {
if ( mergeQueue = = null | | ! this . isAlive ( ) ) {
try {
mergeMount( f1 , f2 , array , payloadrow , newFile ) ;
array. mergeMount( f1 , f2 , payloadrow , newFile ) ;
} catch ( IOException e ) {
e . printStackTrace ( ) ;
}
@ -116,7 +110,7 @@ public class IODispatcher extends Thread {
} catch ( InterruptedException e ) {
e . printStackTrace ( ) ;
try {
mergeMount( f1 , f2 , array , payloadrow , newFile ) ;
array. mergeMount( f1 , f2 , payloadrow , newFile ) ;
} catch ( IOException ee ) {
ee . printStackTrace ( ) ;
}
@ -189,134 +183,12 @@ public class IODispatcher extends Thread {
public File merge ( ) {
try {
return mergeMount( f1 , f2 , array , payloadrow , newFile ) ;
return array. mergeMount( f1 , f2 , payloadrow , newFile ) ;
} catch ( IOException e ) {
e . printStackTrace ( ) ;
}
return null ;
}
}
public static File mergeMount ( File f1 , File f2 , BLOBArray array , Row payloadrow , File newFile ) throws IOException {
System . out . println ( "*** DEBUG mergeOldest: vvvvvvvvv array has " + array . entries ( ) + " entries vvvvvvvvv" ) ;
System . out . println ( "*** DEBUG mergeOldest: unmounted " + f1 . getName ( ) ) ;
System . out . println ( "*** DEBUG mergeOldest: unmounted " + f2 . getName ( ) ) ;
File resultFile = mergeWorker ( f1 , f2 , array , payloadrow , newFile ) ;
if ( resultFile = = null ) return null ;
array . mountBLOB ( resultFile ) ;
System . out . println ( "*** DEBUG mergeOldest: mounted " + newFile . getName ( ) ) ;
System . out . println ( "*** DEBUG mergeOldest: ^^^^^^^^^^^ array has " + array . entries ( ) + " entries ^^^^^^^^^^^" ) ;
return resultFile ;
}
private static File mergeWorker ( File f1 , File f2 , BLOBArray array , Row payloadrow , File newFile ) throws IOException {
// iterate both files and write a new one
CloneableIterator < ReferenceContainer > i1 = new blobFileEntries ( f1 , payloadrow ) ;
CloneableIterator < ReferenceContainer > i2 = new blobFileEntries ( f2 , payloadrow ) ;
if ( ! i1 . hasNext ( ) ) {
if ( i2 . hasNext ( ) ) {
FileUtils . deletedelete ( f1 ) ;
if ( f2 . renameTo ( newFile ) ) return newFile ;
return f2 ;
} else {
FileUtils . deletedelete ( f1 ) ;
FileUtils . deletedelete ( f2 ) ;
return null ;
}
} else if ( ! i2 . hasNext ( ) ) {
FileUtils . deletedelete ( f2 ) ;
if ( f1 . renameTo ( newFile ) ) return newFile ;
return f1 ;
}
assert i1 . hasNext ( ) ;
assert i2 . hasNext ( ) ;
File tmpFile = new File ( newFile . getParentFile ( ) , newFile . getName ( ) + ".tmp" ) ;
HeapWriter writer = new HeapWriter ( tmpFile , newFile , array . keylength ( ) , array . ordering ( ) ) ;
merge ( i1 , i2 , array . ordering ( ) , writer ) ;
try {
writer . close ( true ) ;
// we don't need the old files any more
FileUtils . deletedelete ( f1 ) ;
FileUtils . deletedelete ( f2 ) ;
return newFile ;
} catch ( IOException e ) {
FileUtils . deletedelete ( tmpFile ) ;
FileUtils . deletedelete ( newFile ) ;
e . printStackTrace ( ) ;
return null ;
}
}
private static void merge ( CloneableIterator < ReferenceContainer > i1 , CloneableIterator < ReferenceContainer > i2 , ByteOrder ordering , HeapWriter writer ) throws IOException {
assert i1 . hasNext ( ) ;
assert i2 . hasNext ( ) ;
ReferenceContainer c1 , c2 , c1o , c2o ;
c1 = i1 . next ( ) ;
c2 = i2 . next ( ) ;
int e ;
while ( true ) {
assert c1 ! = null ;
assert c2 ! = null ;
e = ordering . compare ( c1 . getWordHash ( ) . getBytes ( ) , c2 . getWordHash ( ) . getBytes ( ) ) ;
if ( e < 0 ) {
writer . add ( c1 . getWordHash ( ) . getBytes ( ) , c1 . exportCollection ( ) ) ;
if ( i1 . hasNext ( ) ) {
c1o = c1 ;
c1 = i1 . next ( ) ;
assert ordering . compare ( c1 . getWordHash ( ) . getBytes ( ) , c1o . getWordHash ( ) . getBytes ( ) ) > 0 ;
continue ;
}
break ;
}
if ( e > 0 ) {
writer . add ( c2 . getWordHash ( ) . getBytes ( ) , c2 . exportCollection ( ) ) ;
if ( i2 . hasNext ( ) ) {
c2o = c2 ;
c2 = i2 . next ( ) ;
assert ordering . compare ( c2 . getWordHash ( ) . getBytes ( ) , c2o . getWordHash ( ) . getBytes ( ) ) > 0 ;
continue ;
}
break ;
}
assert e = = 0 ;
// merge the entries
writer . add ( c1 . getWordHash ( ) . getBytes ( ) , ( c1 . merge ( c2 ) ) . exportCollection ( ) ) ;
if ( i1 . hasNext ( ) & & i2 . hasNext ( ) ) {
c1 = i1 . next ( ) ;
c2 = i2 . next ( ) ;
continue ;
}
if ( i1 . hasNext ( ) ) c1 = i1 . next ( ) ;
if ( i2 . hasNext ( ) ) c2 = i2 . next ( ) ;
break ;
}
// catch up remaining entries
assert ! ( i1 . hasNext ( ) & & i2 . hasNext ( ) ) ;
while ( i1 . hasNext ( ) ) {
//System.out.println("FLUSH REMAINING 1: " + c1.getWordHash());
writer . add ( c1 . getWordHash ( ) . getBytes ( ) , c1 . exportCollection ( ) ) ;
if ( i1 . hasNext ( ) ) {
c1o = c1 ;
c1 = i1 . next ( ) ;
assert ordering . compare ( c1 . getWordHash ( ) . getBytes ( ) , c1o . getWordHash ( ) . getBytes ( ) ) > 0 ;
continue ;
}
break ;
}
while ( i2 . hasNext ( ) ) {
//System.out.println("FLUSH REMAINING 2: " + c2.getWordHash());
writer . add ( c2 . getWordHash ( ) . getBytes ( ) , c2 . exportCollection ( ) ) ;
if ( i2 . hasNext ( ) ) {
c2o = c2 ;
c2 = i2 . next ( ) ;
assert ordering . compare ( c2 . getWordHash ( ) . getBytes ( ) , c2o . getWordHash ( ) . getBytes ( ) ) > 0 ;
continue ;
}
break ;
}
// finished with writing
}
}