📄 diphoneunitdatabase.java
字号:
*/ public void dumpBinary(String path) { try { FileOutputStream fos = new FileOutputStream(path); DataOutputStream os = new DataOutputStream(fos); int written; os.writeInt(MAGIC); os.writeInt(VERSION); os.writeInt(sampleRate); os.writeInt(numChannels); os.writeFloat(lpcMin); os.writeFloat(lpcRange); os.writeInt(diphoneMap.size()); for (Iterator i = diphoneMap.values().iterator(); i.hasNext();) { Diphone diphone = (Diphone) i.next(); diphone.dumpBinary(os); } os.flush(); fos.close(); } catch (FileNotFoundException fe) { throw new Error("Can't dump binary database " + fe.getMessage()); } catch (IOException ioe) { throw new Error("Can't write binary database " + ioe.getMessage()); } } /** * Dumps a binary index. The database index is used if our * cacheType is not set to 'preload' and we are loading a binary * database. The index is a simple mapping of diphone names (the * key) to the file position in the database. In situations where * the entire database is not preloaded, this index can be loaded * and used to provide quicker startup (since only the index need * be loaded at startup) and quick access to the diphone data. * * @param path the path to dump the file to */ void dumpBinaryIndex(String path) { try { FileOutputStream fos = new FileOutputStream(path); DataOutputStream dos = new DataOutputStream(fos); dos.writeInt(INDEX_MAGIC); dos.writeInt(diphoneIndex.keySet().size()); for (Iterator i = diphoneIndex.keySet().iterator(); i.hasNext();) { String key = (String) i.next(); int pos = ((Integer) diphoneIndex.get(key)).intValue(); dos.writeUTF(key); dos.writeInt(pos); } dos.close(); } catch (FileNotFoundException fe) { throw new Error("Can't dump binary index " + fe.getMessage()); } catch (IOException ioe) { throw new Error("Can't write binary index " + ioe.getMessage()); } } /** * Loads a binary index. * * @param url the location of the binary index file */ private void loadBinaryIndex(URL url) { diphoneIndex = new HashMap(); try { InputStream is = Utilities.getInputStream(url); DataInputStream dis = new DataInputStream(is); if (dis.readInt() != INDEX_MAGIC) { throw new Error("Bad index file format"); } int size = dis.readInt(); for (int i = 0; i < size; i++) { String diphoneName = dis.readUTF(); int pos = dis.readInt(); diphoneIndex.put(diphoneName, new Integer(pos)); } dis.close(); } catch (FileNotFoundException fe) { throw new Error("Can't load binary index " + fe.getMessage()); } catch (IOException ioe) { throw new Error("Can't read binary index " + ioe.getMessage()); } } /** * Gets the index for the given diphone. * * @param diphone the name of the diphone * * @return the index into the database for the diphone */ private int getIndex(String diphone) { Integer index = (Integer) diphoneIndex.get(diphone); if (index != null) { int idx = index.intValue(); if (defaultIndex == -1) { defaultIndex = idx; } return idx; } else { System.out.println("Can't find index entry for " + diphone); return defaultIndex; } } /** * Loads a binary file from the input stream. * <p> * Note that we currently have four! methods of loading up the * database. We were interested in the performance characteristics * of the various methods of loading the database so we coded it * all up. * * @param is the input stream to read the database * from * * @throws IOException if there is trouble opening the DB * */ private void loadBinary(InputStream is) throws IOException { // we get better performance if we can map the file in // 1.0 seconds vs. 1.75 seconds, but we can't // always guarantee that we can do that. if (useNewIO && is instanceof FileInputStream) { FileInputStream fis = (FileInputStream) is; if (useIndexing) { loadBinaryIndex(new URL(indexName)); mapDatabase(fis); } else { loadMappedBinary(fis); } } else { DataInputStream dis = new DataInputStream( new BufferedInputStream(is)); loadBinary(dis); } } /** * Loads the binary data from the given input stream. * * @param dis the data input stream. */ private void loadBinary(DataInputStream dis) throws IOException { int size; if (dis.readInt() != MAGIC) { throw new Error("Bad magic in db"); } if (dis.readInt() != VERSION) { throw new Error("Bad VERSION in db"); } sampleRate = dis.readInt(); numChannels = dis.readInt(); lpcMin = dis.readFloat(); lpcRange = dis.readFloat(); size = dis.readInt(); for (int i = 0; i < size; i++) { Diphone diphone = Diphone.loadBinary(dis); add(diphone); } } /** * Loads the database from the given FileInputStream. * * @param is the InputStream to load the database from * * @throws IOException if there is trouble opening the DB */ private void loadMappedBinary(FileInputStream is) throws IOException { FileChannel fc = is.getChannel(); MappedByteBuffer bb = fc.map(FileChannel.MapMode.READ_ONLY, 0, (int) fc.size()); bb.load(); loadDatabase(bb); is.close(); } /** * Maps the database from the given FileInputStream. * * @param is the InputStream to load the database from * * @throws IOException if there is trouble opening the DB */ private void mapDatabase(FileInputStream is) throws IOException { FileChannel fc = is.getChannel(); mbb = fc.map(FileChannel.MapMode.READ_ONLY, 0, (int) fc.size()); mbb.load(); loadDatabaseHeader(mbb); } /** * Loads the database header from the given byte buffer. * * @param bb the byte buffer to load the db from * * @throws IOException if there is trouble opening the DB */ private void loadDatabaseHeader(ByteBuffer bb) throws IOException { if (bb.getInt() != MAGIC) { throw new Error("Bad magic in db"); } if (bb.getInt() != VERSION) { throw new Error("Bad VERSION in db"); } sampleRate = bb.getInt(); numChannels = bb.getInt(); lpcMin = bb.getFloat(); lpcRange = bb.getFloat(); } /** * Loads the database from the given byte buffer. * * @param bb the byte buffer to load the db from * * @throws IOException if there is trouble opening the DB */ private void loadDatabase(ByteBuffer bb) throws IOException { int size; loadDatabaseHeader(bb); size = bb.getInt(); diphoneIndex = new HashMap(); for (int i = 0; i < size; i++) { int pos = bb.position(); Diphone diphone = Diphone.loadBinary(bb); add(diphone); diphoneIndex.put(diphone.getName(), new Integer(pos)); } } /** * Compares this database to another. This is used for testing. * With this method we can load up two databases (one perhaps from * a text source and one from a binary source) and compare to * verify that the dbs are identical * * @param other the other database * * @return <code>true</code> if the DBs are identical; * otherwise <code>false</code> */ public boolean compare(DiphoneUnitDatabase other) { if (sampleRate != other.sampleRate) { return false; } if (numChannels != other.numChannels) { return false; } if (lpcMin != other.lpcMin) { return false; } if (lpcRange != other.lpcRange) { return false; } for (Iterator i = diphoneMap.values().iterator(); i.hasNext(); ) { Diphone diphone = (Diphone) i.next(); Diphone otherDiphone = (Diphone) other.getUnit(diphone.getName()); if (!diphone.compare(otherDiphone)) { System.out.println("Diphones differ:"); System.out.println("THis:"); diphone.dump(); System.out.println("Other:"); otherDiphone.dump(); return false; } } return true; } /** * Manipulates a DiphoneUnitDatabase. This program is typically * used to generate the binary form (with index) of the * DiphoneUnitDatabase from the text form. Additionally, this program * can be used to compare two databases to see if they are * identical (used for testing). * * <p> * <b> Usage </b> * <p> * <code> java com.sun.speech.freetts.diphone.DiphoneUnitDatabase * [options]</code> * <p> * <b> Options </b> * <p> * <ul> * <li> <code> -src path </code> provides a directory * path to the source text for the database * <li> <code> -dest path </code> provides a directory * for where to place the resulting binaries * <li> <code> -generate_binary [filename] </code> * reads in the text * version of the database and generates the binary * version of the database. * <li> <code> -compare </code> Loads the text and * binary versions of the database and compares them to * see if they are equivalent. * <li> <code> -showTimes </code> shows timings for any * loading, comparing or dumping operation * </ul> * */ public static void main(String[] args) { boolean showTimes = false; String srcPath = "."; String destPath = "."; try { if (args.length > 0) { BulkTimer timer = BulkTimer.LOAD; timer.start(); for (int i = 0 ; i < args.length; i++) { if (args[i].equals("-src")) { srcPath = args[++i]; } else if (args[i].equals("-dest")) { destPath = args[++i]; } else if (args[i].equals("-generate_binary")) { String name = "diphone_units.txt"; if (i + 1 < args.length) { String nameArg = args[++i]; if (!nameArg.startsWith("-")) { name = nameArg; } } int suffixPos = name.lastIndexOf(".txt"); String binaryName = "diphone_units.bin"; if (suffixPos != -1) { binaryName = name.substring(0, suffixPos) + ".bin"; } String indexName = "diphone_units.idx"; if (suffixPos != -1) { indexName = name.substring(0, suffixPos) + ".idx"; } System.out.println("Loading " + name); timer.start("load_text"); DiphoneUnitDatabase udb = new DiphoneUnitDatabase( new URL("file:" + srcPath + "/" + name), false); timer.stop("load_text"); System.out.println("Dumping " + binaryName); timer.start("dump_binary"); udb.dumpBinary(destPath + "/" + binaryName); timer.stop("dump_binary"); timer.start("load_binary"); DiphoneUnitDatabase budb = new DiphoneUnitDatabase( new URL("file:" + destPath + "/" + binaryName), true); timer.stop("load_binary"); System.out.println("Dumping " + indexName); timer.start("dump index"); budb.dumpBinaryIndex(destPath + "/" + indexName); timer.stop("dump index"); } else if (args[i].equals("-compare")) { timer.start("load_text"); DiphoneUnitDatabase udb = new DiphoneUnitDatabase( new URL("file:./diphone_units.txt"), false); timer.stop("load_text"); timer.start("load_binary"); DiphoneUnitDatabase budb = new DiphoneUnitDatabase( new URL("file:./diphone_units.bin"), true); timer.stop("load_binary"); timer.start("compare"); if (udb.compare(budb)) { System.out.println("other compare ok"); } else { System.out.println("other compare different"); } timer.stop("compare"); } else if (args[i].equals("-showtimes")) { showTimes = true; } else { System.out.println("Unknown option " + args[i]); } } timer.stop(); if (showTimes) { timer.show("DiphoneUnitDatabase"); } } else { System.out.println("Options: "); System.out.println(" -src path"); System.out.println(" -dest path"); System.out.println(" -compare"); System.out.println(" -generate_binary"); System.out.println(" -showTimes"); } } catch (IOException ioe) { System.err.println(ioe); } }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -