diff options
author | James Ahlborn <jtahlborn@yahoo.com> | 2019-08-06 21:17:25 +0000 |
---|---|---|
committer | James Ahlborn <jtahlborn@yahoo.com> | 2019-08-06 21:17:25 +0000 |
commit | 6a189ba076b4484bbb2bf3d55c7aa4160ed7fde1 (patch) | |
tree | 530cee5812ca2551e7802ec0b7a657b51b484a71 /src/main/java | |
parent | 67a77c7aca654900fe81910df1ebaa4233847836 (diff) | |
download | jackcess-6a189ba076b4484bbb2bf3d55c7aa4160ed7fde1.tar.gz jackcess-6a189ba076b4484bbb2bf3d55c7aa4160ed7fde1.zip |
initial index codes for access97 general collation order
git-svn-id: https://svn.code.sf.net/p/jackcess/code/jackcess/branches/a97_indexes@1304 f203690c-595d-4dc9-a70b-905162fa7fd2
Diffstat (limited to 'src/main/java')
-rw-r--r-- | src/main/java/com/healthmarketscience/jackcess/impl/General97IndexCodes.java | 127 |
1 files changed, 127 insertions, 0 deletions
diff --git a/src/main/java/com/healthmarketscience/jackcess/impl/General97IndexCodes.java b/src/main/java/com/healthmarketscience/jackcess/impl/General97IndexCodes.java new file mode 100644 index 0000000..432a0a9 --- /dev/null +++ b/src/main/java/com/healthmarketscience/jackcess/impl/General97IndexCodes.java @@ -0,0 +1,127 @@ +/* +Copyright (c) 2019 James Ahlborn + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package com.healthmarketscience.jackcess.impl; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStreamReader; + +import static com.healthmarketscience.jackcess.impl.ByteUtil.ByteStream; + +/** + * Various constants used for creating "general" (access 1997) sort order + * text index entries. + * + * @author James Ahlborn + */ +public class General97IndexCodes extends GeneralLegacyIndexCodes +{ + // stash the codes in some resource files + private static final String CODES_FILE = + DatabaseImpl.RESOURCE_PATH + "index_codes_gen_97.txt"; + private static final String EXT_MAPPINGS_FILE = + DatabaseImpl.RESOURCE_PATH + "index_mappings_ext_gen_97.txt"; + + private static final class Codes + { + /** handlers for the first 256 chars. use nested class to lazy load the + handlers */ + private static final CharHandler[] _values = loadCodes( + CODES_FILE, FIRST_CHAR, LAST_CHAR); + } + + private static final class ExtMappings + { + /** mappings for the rest of the chars in BMP 0. use nested class to lazy + load the handlers. since these codes are for single byte encodings, + you would think you wou;dn't need any ext codes. however, some chars + in the extended range have corollaries in the single byte range. this + array holds the mappings from the ext range to the single byte range. + chars without mappings go to 0. */ + private static final short[] _values = loadMappings( + EXT_MAPPINGS_FILE, FIRST_EXT_CHAR, LAST_EXT_CHAR); + } + + static final General97IndexCodes GEN_97_INSTANCE = new General97IndexCodes(); + + General97IndexCodes() {} + + /** + * Returns the CharHandler for the given character. + */ + @Override + CharHandler getCharHandler(char c) + { + if(c <= LAST_CHAR) { + return Codes._values[c]; + } + + // some ext chars are equivalent to single byte chars. most chars have no + // equivalent, and they map to 0 (which is an "ignored" char, so it all + // works out) + int extOffset = asUnsignedChar(c) - asUnsignedChar(FIRST_EXT_CHAR); + return Codes._values[ExtMappings._values[extOffset]]; + } + + @Override + void writeNonNullIndexTextValue( + Object value, ByteStream bout, boolean isAscending) + throws IOException + { + // use simplified format for 97 encoding + writeNonNull97IndexTextValue(value, bout, isAscending); + } + + static short[] loadMappings(String mappingsFilePath, + char firstChar, char lastChar) + { + int firstCharCode = asUnsignedChar(firstChar); + int numMappings = (asUnsignedChar(lastChar) - firstCharCode) + 1; + short[] values = new short[numMappings]; + + BufferedReader reader = null; + try { + + reader = new BufferedReader( + new InputStreamReader( + DatabaseImpl.getResourceAsStream(mappingsFilePath), "US-ASCII")); + + // this is a sparse file with entries like <fromCode>,<toCode> + String mappingLine = null; + while((mappingLine = reader.readLine()) != null) { + mappingLine = mappingLine.trim(); + if(mappingLine.length() == 0) { + continue; + } + + String[] mappings = mappingLine.split(","); + int fromCode = Integer.parseInt(mappings[0]); + int toCode = Integer.parseInt(mappings[1]); + + values[fromCode - firstCharCode] = (short)toCode; + } + + } catch(IOException e) { + throw new RuntimeException("failed loading index mappings file " + + mappingsFilePath, e); + } finally { + ByteUtil.closeQuietly(reader); + } + + return values; + } +} |