From cb361b8046c9564e2250c49db88894dd1b8ae851 Mon Sep 17 00:00:00 2001 From: JG1VPP Date: Sun, 2 Jun 2024 23:10:34 +0900 Subject: [PATCH] BasicFactory.FieldSet --- src/main/java/gaas/table/CBinDecoder.java | 20 +- src/main/java/gaas/table/CBinEncoder.java | 23 +-- src/main/java/gaas/table/CBinFactory.java | 215 ++++++--------------- src/main/java/qxsl/table/BasicFactory.java | 107 +++++----- 4 files changed, 145 insertions(+), 220 deletions(-) diff --git a/src/main/java/gaas/table/CBinDecoder.java b/src/main/java/gaas/table/CBinDecoder.java index ad8c58a5..82438f2b 100644 --- a/src/main/java/gaas/table/CBinDecoder.java +++ b/src/main/java/gaas/table/CBinDecoder.java @@ -10,14 +10,16 @@ import java.io.InputStream; import java.util.Arrays; +import qxsl.draft.Band; +import qxsl.draft.Mode; import qxsl.draft.Qxsl; import qxsl.model.Item; import qxsl.model.Node; import qxsl.table.BasicDecoder; -import gaas.table.CBinFactory.BandEnum; import gaas.table.CBinFactory.DateTime; -import gaas.table.CBinFactory.ModeEnum; + +import static qxsl.table.BasicFactory.FieldSet; /** * LG8書式で永続化された交信記録を解読します。 @@ -29,7 +31,9 @@ */ public final class CBinDecoder extends BasicDecoder { private final DataInputStream source; - private DateTime cDTime; + private final FieldSet bandSet; + private final FieldSet modeSet; + private final DateTime chrono; private int numQSOs; /** @@ -41,7 +45,9 @@ public final class CBinDecoder extends BasicDecoder { public CBinDecoder(InputStream stream) { super("cbin"); this.source = new DataInputStream(stream); - this.cDTime = new DateTime(); + this.chrono = new DateTime(); + this.bandSet = CBinFactory.getBandSet(); + this.modeSet = CBinFactory.getModeSet(); } /** @@ -157,7 +163,7 @@ private final String read(int max) throws IOException { * @throws IOException 読み取りに失敗した場合 */ private final void time(Node node) throws IOException { - node.set(cDTime.decode(source.readLong())); + node.set(chrono.decode(source.readLong())); } /** @@ -193,7 +199,7 @@ private final void code(Node node) throws IOException { * @throws IOException 読み取りに失敗した場合 */ private final void mode(Node node) throws IOException { - node.set(ModeEnum.forIndex(source.read()).toMode()); + node.set(modeSet.valueOf(source.read())); } /** @@ -205,7 +211,7 @@ private final void mode(Node node) throws IOException { * @throws IOException 読み取りに失敗した場合 */ private final void band(Node node) throws IOException { - node.set(BandEnum.forIndex(source.read()).toBand()); + node.set(bandSet.valueOf(source.read())); } /** diff --git a/src/main/java/gaas/table/CBinEncoder.java b/src/main/java/gaas/table/CBinEncoder.java index 29255562..80d54cee 100644 --- a/src/main/java/gaas/table/CBinEncoder.java +++ b/src/main/java/gaas/table/CBinEncoder.java @@ -20,9 +20,9 @@ import qxsl.table.BasicEncoder; import qxsl.value.Field; -import gaas.table.CBinFactory.BandEnum; import gaas.table.CBinFactory.DateTime; -import gaas.table.CBinFactory.ModeEnum; + +import static qxsl.table.BasicFactory.FieldSet; /** * 標準構造の交信記録をLG8書式で永続化します。 @@ -34,7 +34,9 @@ */ public final class CBinEncoder extends BasicEncoder { private final DataOutputStream target; - private final DateTime cDTime; + private final FieldSet bandSet; + private final FieldSet modeSet; + private final DateTime chrono; private final Set names; private Item last; private int count; @@ -48,8 +50,10 @@ public final class CBinEncoder extends BasicEncoder { public CBinEncoder(OutputStream stream) { super("cbin"); this.names = new LinkedHashSet(); + this.chrono = new DateTime(); this.target = new DataOutputStream(stream); - this.cDTime = new DateTime(); + this.bandSet = CBinFactory.getBandSet(); + this.modeSet = CBinFactory.getModeSet(); } /** @@ -195,8 +199,7 @@ private final void names() throws IOException { * @throws IOException 書き込みに失敗した場合 */ private final void time(Time time) throws IOException { - if(time == null) target.write(new byte[8]); - else target.writeLong(cDTime.encode(time)); + target.writeLong(chrono.encode(time)); } /** @@ -208,9 +211,8 @@ private final void time(Time time) throws IOException { * @throws IOException 書き込みに失敗した場合 */ private final void mode(Mode mode) throws IOException { - final var modes = ModeEnum.valueOf(mode); if(mode == null) target.writeByte(0); - else target.writeByte(modes.ordinal()); + else target.writeByte(modeSet.indexOf(mode)); } /** @@ -222,8 +224,7 @@ private final void mode(Mode mode) throws IOException { * @throws IOException 書き込みに失敗した場合 */ private final void band(Band band) throws IOException { - final var bands = BandEnum.valueOf(band); - if(bands == null) target.writeByte(0); - else target.writeByte(bands.ordinal()); + if(band == null) target.writeByte(0); + else target.writeByte(bandSet.indexOf(band)); } } diff --git a/src/main/java/gaas/table/CBinFactory.java b/src/main/java/gaas/table/CBinFactory.java index 7cce4a5b..986e1e5b 100644 --- a/src/main/java/gaas/table/CBinFactory.java +++ b/src/main/java/gaas/table/CBinFactory.java @@ -63,173 +63,76 @@ public final TableEncoder encoder(OutputStream os) { } /** - * LG8書式の周波数帯の列挙型です。 + * この書式が対応する周波数帯の集合を返します。 * * - * @author 無線部開発班 + * @return 周波数帯の集合 * - * @since 2017/06/12 + * @since 2024/06/02 */ - public enum BandEnum { - M1_9 ( 1900), - M3_5 ( 3500), - M7 ( 7000), - M10 ( 10000), - M14 ( 14000), - M18 ( 18000), - M21 ( 21000), - M24 ( 24000), - M28 ( 28000), - M50 ( 50000), - M144 ( 144000), - M430 ( 430000), - M1200( 1200000), - M2400( 2400000), - M5600( 5600000), - G10 ( 10000000), - G24 ( 24000000), - G47 ( 47000000), - G75 ( 75000000), - G77 ( 77000000), - G135 (135000000), - G248 (248000000), - K136 ( 136); - - private final Band band; - - /** - * 周波数帯を指定して列挙子を生成します。 - * - * - * @param kHz 周波数帯 - */ - private BandEnum(int kHz) { - this.band = new Band(kHz); - } - - @Override - public String toString() { - return band.toString(); - } - - /** - * この列挙子に対応する周波数帯を返します。 - * - * - * @return 周波数帯 - */ - public Band toBand() { - return band; - } - - /** - * 指定された周波数に対応する列挙子を返します。 - * - * - * @param band 周波数 - * - * @return 対応する列挙子があれば返す - */ - public static BandEnum valueOf(Band band) { - for(var v: values()) if(v.band.equals(band)) return v; - return null; - } - - /** - * 指定された序数に対応する列挙子を返します。 - * - * - * @param band 序数 - * - * @return 対応する列挙子があれば返す - */ - public static BandEnum forIndex(int band) { - for(var v: values()) if(v.ordinal() == band) return v; - return null; - } + public static final FieldSet getBandSet() { + final var set = new FieldSet("bands"); + set.add(new Band( 1900)); + set.add(new Band( 3500)); + set.add(new Band( 7000)); + set.add(new Band( 10000)); + set.add(new Band( 14000)); + set.add(new Band( 18000)); + set.add(new Band( 21000)); + set.add(new Band( 24000)); + set.add(new Band( 28000)); + set.add(new Band( 50000)); + set.add(new Band( 144000)); + set.add(new Band( 430000)); + set.add(new Band( 1200000)); + set.add(new Band( 2400000)); + set.add(new Band( 5600000)); + set.add(new Band( 10000000)); + set.add(new Band( 24000000)); + set.add(new Band( 47000000)); + set.add(new Band( 75000000)); + set.add(new Band( 77000000)); + set.add(new Band(135000000)); + set.add(new Band(248000000)); + set.add(new Band( 136)); + return set; } /** - * LG8書式の通信方式の列挙型です。 + * この書式が対応する通信方式の集合を返します。 * * - * @author 無線部開発班 + * @return 通信方式の集合 * - * @since 2017/06/12 + * @since 2024/06/02 */ - public enum ModeEnum { - CW ("CW"), - RTTY ("RTTY"), - SSB ("SSB"), - FM ("FM"), - AM ("AM"), - ATV ("ATV"), - SSTV ("SSTV"), - PSK ("PSK"), - GMSK ("GMSK"), - MFSK ("MFSK"), - QPSK ("QPSK"), - FSK ("FSK"), - DSTAR ("D-STAR"), - C4FM ("C4FM"), - JT65 ("JT65"), - JT9 ("JT9"), - ISCAT ("ISCAT"), - FT8 ("FT8"), - JT4 ("JT4"), - QRA64 ("QRA64"), - MSK144 ("MSK144"), - WSPR ("WSPR"), - JTMS ("JTMS"), - FT4 ("FT4"); - - private final Mode mode; - - /** - * 通信方式を指定して列挙子を生成します。 - * - * - * @param mode 通信方式 - */ - private ModeEnum(String mode) { - this.mode = new Mode(mode); - } - - /** - * この列挙子に対応するモードを返します。 - * - * - * @return モード - */ - public Mode toMode() { - return mode; - } - - /** - * 指定されたモードに対応する列挙子を返します。 - * - * - * @param mode モード - * - * @return 対応する列挙子があれば返す - */ - public static ModeEnum valueOf(Mode mode) { - for(var v: values()) if(v.mode.equals(mode)) return v; - return null; - } - - /** - * 指定された序数に対応する列挙子を返します。 - * - * - * @param mode 序数 - * - * @return 対応する列挙子があれば返す - */ - public static ModeEnum forIndex(int mode) { - for(var v: values()) if(v.ordinal() == mode) return v; - return null; - } + public static final FieldSet getModeSet() { + final var set = new FieldSet("modes"); + set.add(new Mode("CW")); + set.add(new Mode("RTTY")); + set.add(new Mode("SSB")); + set.add(new Mode("FM")); + set.add(new Mode("AM")); + set.add(new Mode("ATV")); + set.add(new Mode("SSTV")); + set.add(new Mode("PSK")); + set.add(new Mode("GMSK")); + set.add(new Mode("MFSK")); + set.add(new Mode("QPSK")); + set.add(new Mode("FSK")); + set.add(new Mode("D-STAR")); + set.add(new Mode("C4FM")); + set.add(new Mode("JT65")); + set.add(new Mode("JT9")); + set.add(new Mode("ISCAT")); + set.add(new Mode("FT8")); + set.add(new Mode("JT4")); + set.add(new Mode("QRA64")); + set.add(new Mode("MSK144")); + set.add(new Mode("WSPR")); + set.add(new Mode("JTMS")); + set.add(new Mode("FT4")); + return set; } /** diff --git a/src/main/java/qxsl/table/BasicFactory.java b/src/main/java/qxsl/table/BasicFactory.java index dac249c3..b14f870d 100644 --- a/src/main/java/qxsl/table/BasicFactory.java +++ b/src/main/java/qxsl/table/BasicFactory.java @@ -5,15 +5,14 @@ *******************************************************************************/ package qxsl.table; +import java.io.IOException; import java.io.UncheckedIOException; -import java.time.Year; -import java.time.format.DateTimeFormatter; -import java.time.format.DateTimeFormatterBuilder; -import java.time.temporal.ChronoField; +import java.util.LinkedList; import java.util.List; import java.util.Properties; import qxsl.utils.AssetUtil; +import qxsl.value.Field; /** * 書式の説明を設定ファイルから取得する機能を提供します。 @@ -98,54 +97,70 @@ public final List extensions() { } /** - * この書式のヘッダとなる文字列を返します。 + * この書式が対応する属性値を列挙する集合です。 * * - * @return ヘッダの文字列 - * - * @since 2019/07/11 - */ - public final String getHeaderText() { - return get("head-text").replaceAll("^\\R+|\\R+$", ""); - } - - /** - * この書式の入力時に使う時刻の書式を返します。 + * @author 無線部開発班 * + * @since 2024/06/02 * - * @return 時刻の書式 - * - * @since 2020/09/06 + * @param 属性値の総称型 */ - public final DateTimeFormatter getTimeDecoderOld() { - final var pattern = get("time-decoder"); - final int current = Year.now().getValue(); - final var factory = new DateTimeFormatterBuilder(); - factory.parseDefaulting(ChronoField.YEAR, current); - return factory.appendPattern(pattern).toFormatter(); - } + public static final class FieldSet> { + private final List list; + private final String name; - /** - * この書式の出力時に使う時刻の書式を返します。 - * - * - * @return 時刻の書式 - * - * @since 2020/09/06 - */ - public final DateTimeFormatter getTimeDecoder() { - return DateTimeFormatter.ofPattern(get("time-decoder")); - } + /** + * 属性値の列挙子の集合を構築します。 + * + * + * @param name 属性の名前 + */ + public FieldSet(String name) { + this.name = name; + this.list = new LinkedList<>(); + } - /** - * この書式の出力時に使う時刻の書式を返します。 - * - * - * @return 時刻の書式 - * - * @since 2020/09/06 - */ - public final DateTimeFormatter getTimeEncoder() { - return DateTimeFormatter.ofPattern(get("time-encoder")); + /** + * 指定された属性を末尾に追加します。 + * + * + * @param field 属性 + */ + public final void add(F field) { + this.list.add(field); + } + + /** + * 指定された序数の属性値を返します。 + * + * + * @param index 序数 + * + * @return 属性値 + * + * @throws IOException 範囲外の場合 + */ + public final F valueOf(int index) throws IOException { + if(list.size() > index) return list.get(index); + final var msg = "index %d is not registered within %s"; + throw new IOException(String.format(msg, index, name)); + } + + /** + * 指定された属性値の序数を返します。 + * + * + * @param value 属性値 + * + * @return 対応する列挙子があれば返す + * + * @throws IOException 範囲外の場合 + */ + public final int indexOf(F value) throws IOException { + if(list.contains(value)) return list.indexOf(value); + final var msg = "value %s is not registered within %s"; + throw new IOException(String.format(msg, value, name)); + } } }