import java.io.File;
import java.io.RandomAccessFile;
import java.io.IOException;
public class LZW
{
private int dictionaryIndexToPrint = 0;
private boolean wasInDictionary = false;
public static String g_fileExtension = new String();
public void compress(File file)
{
if(file.exists() != true)
{
System.out.println("Datei existiert nicht, programm wird beendet");
return;
}
try{
File comFile = new File(newFileName(file));
comFile.createNewFile();
FileHeader fh = new FileHeader(comFile);
fh.writeHeader();
RandomAccessFile fileReader = new RandomAccessFile(file, "r");
RandomAccessFile fileWriter = new RandomAccessFile(comFile, "rw");
System.out.println("Die Originaldatei " + file.getName() + " hat eine groesse von " + fileReader.length() + " Bytes\n");
short gelesenesByte;
String puffer = new String();
short index = 256;
String[][] codeTable = new String[(int)fileReader.length()][2];
for(long i = 0; i < fileReader.length(); i++)
codeTable[(int)i][0] = "";
System.out.println("Lesen\tCodetabelle\tAusgabe\t\tPuffer");
for(long i = 0; i < fileReader.length(); i++)
{
gelesenesByte = (short)fileReader.read();
if(i == 0)
{
puffer = Integer.toString(gelesenesByte);
System.out.printf("%5s %40s\n", String.valueOf(gelesenesByte), puffer);
continue;
}
if(isAlreadyInCodeTable(codeTable, new String(puffer + Integer.toString(gelesenesByte)), i) == false)
{
codeTable[(int)i][0] = "" + puffer + gelesenesByte;
codeTable[(int)i][1] = Integer.toString(index);
index++;
if(wasInDictionary == false)
{
System.out.printf("%5s %13s %11s %14s\n", String.valueOf(gelesenesByte), puffer + String.valueOf(gelesenesByte), puffer, String.valueOf(gelesenesByte));
fileWriter.writeShort(Integer.parseInt(puffer));
}
else
{
System.out.printf("%5s %13s %11s %14s\n", String.valueOf(gelesenesByte), puffer + String.valueOf(gelesenesByte), dictionaryIndexToPrint, String.valueOf(gelesenesByte));
fileWriter.writeShort(dictionaryIndexToPrint);
}
puffer = Integer.toString(gelesenesByte);
wasInDictionary = false;
}
else
{
puffer += gelesenesByte;
}
}
System.out.printf("EOF %42s", puffer);
fileWriter.writeShort(Short.parseShort(puffer));
System.out.println("\nDie komprimierte Datei hat eine groesse von " + fileWriter.length() + " Bytes");
fileReader.close();
fileWriter.close();
} catch(IOException e) {
}
}
private String newFileName(File file)
{
String s = file.getName();
String path = file.getAbsolutePath();
int indexPath = path.lastIndexOf(s);
path = path.substring(0, indexPath);
int index = s.lastIndexOf(".");
g_fileExtension = s.substring(index +1, s.length());
s = s.substring(0, index) + ".mip";
path += s;
return path;
}
private boolean isAlreadyInCodeTable(String[][] ct, String s, long lCounter)
{
for(long i = 0; i < lCounter; i++)
{
if(ct[(int)i][0].equals(s))
{
dictionaryIndexToPrint = Integer.parseInt(ct[(int)i][1]);
wasInDictionary = true;
return true;
}
}
return false;
}
private String origFileName(File file)
{
FileHeader fh = new FileHeader(file);
String ext = new String(fh.readHeader());
String path = file.getAbsolutePath();
int index = path.lastIndexOf(".");
path = path.substring(0, index) + ext;
return path;
}
public void decompress(File file)
{
if(file.exists() != true)
{
System.out.println("Datei existiert nicht, programm wird beendet");
return;
}
try{
File decomFile = new File(origFileName(file));
decomFile.createNewFile();
RandomAccessFile fileReader = new RandomAccessFile(file, "r");
RandomAccessFile fileWriter = new RandomAccessFile(decomFile, "rw");
short geleseneZweiByte;
String letztesWort = "";
String codeTable[][] = new String[(int)fileReader.length()][2];
int index = 256;
for(long i = 0; i < fileReader.length(); i++)
codeTable[(int)i][0] = "";
for(long i = 0; i < fileReader.length(); i++)
{
geleseneZweiByte = (short)fileReader.readUnsignedShort();
if(i == 0)
{
fileWriter.writeBytes(String.format("%C", geleseneZweiByte));
letztesWort = Short.toString(geleseneZweiByte);
continue;
}
if(geleseneZweiByte <= 255)
{
fileWriter.writeBytes(String.format("%C", geleseneZweiByte));
if(isAlreadyInCodeTable(codeTable, new String(letztesWort + Short.toString(geleseneZweiByte)), i) == false)
{
codeTable[(int)i][0] = letztesWort + Short.toString(geleseneZweiByte);
codeTable[(int)i][1] = Integer.toString(index);
index++;
}
continue;
}
if(geleseneZweiByte > 255)
{
for(int j = 0; j < i; j++)
{
if(codeTable[j][1] == Short.toString(geleseneZweiByte))
{
fileWriter.writeBytes(codeTable[j][0]);
}
}
}
}
} catch(IOException e) {
}
}