考虑到ISO 4217 数字货币代码,我尝试使用正确的格式规则格式化金额。
例如,给定金额99.99和数字代码840,我希望产生一个字符串' USD 99.99'或类似的。
看看JSR 354的实现,似乎我需要先找到合适的货币单位。但是,我似乎无法为此目的撰写有效的CurrencyQuery。
鉴于
CurrencyQuery query = CurrencyQueryBuilder.of().setNumericCodes(840).build();
CurrencyUnit cu = Monetary.getCurrency(query);
MonetaryAmount amount = FastMoney.of(99.99, cu);
System.out.println(MonetaryFormats.getAmountFormat(Locale.ENGLISH).format(amount));
我收到以下例外:
Exception in thread "main" javax.money.MonetaryException: Ambiguous request for CurrencyUnit: CurrencyQuery (
{Query.numericCodes=[840]}), found: [BIF, ARS, DZD, COP, CVE, CHF, HRK, IQD, LAK, XPF, DKK, BAM, ZMK, ITL, XBB, XUA, XPT, BRL, CAD, NZD, SEK, USN, XTS, IEP, SRG, STD, BHD, USS, XAF, AUD, CDF, MTL, QAR, AOA, MGA, TOP, LYD, BOV, ISK, ADP, HTG, IDR, ANG, XXX, BTN, KHR, LTL, KES, INR, MGF, OMR, BEF, EUR, BOB, JPY, XBA, AED, SOS, XPD, SKK, FKP, XBC, CRC, SCR, MYR, MZN, LVL, GYD, XDR, GHS, XCD, MDL, MRO, ZWN, LSL, PEN, ATS, XOF, AZM, BYB, TRY, SRD, TTD, IRR, NOK, BZD, TRL, BDT, KZT, CLF, SLL, USD, ETB, BSD, SDD, UYU, ESP, VEB, TMM, CUP, NAD, DOP, NPR, TJS, VND, ZWR, AMD, FRF, TWD, LUF, GNF, MOP, MKD, JMD, CZK, PTE, LBP, ZWD, RSD, FIM, AZN, SDG, GHC, THB, MMK, BBD, PLN, ROL, NGN, RON, TZS, ERN, GBP, TPE, UZS, XBD, SGD, MXV, SVC, FJD, GWP, CNY, BYR, RUB, CSD, XAG, HKD, BND, SHP, KPW, CLP, KYD, DJF, ILS, RUR, LRD, SYP, SAR, ZWL, VUV, DEM, XSU, SIT, PHP, PYG, TND, HNL, ZAR, XFO, BMD, MWK, ZMW, UGX, NLG, JOD, KWD, YER, GMD, CUC, BGL, RWF, UAH, MVR, AWG, MZM, LKR, CYP, VEF, BWP, MXN, KRW, TMT, GIP, MUR, MNT, EEK, GTQ, PKR, PAB, KGS, GRD, YUM, SZL, GEL, WST, MAD, EGP, SBD, ALL, PGK, NIO, AFA, BGN, XAU, SSP, AFN, HUF, XFU, AYM, KMF]
我该如何撰写货币查询?还有更好的方法吗?
TestCurrencyQuery.java :
package test;
import java.util.Locale;
import javax.money.CurrencyQuery;
import javax.money.CurrencyQueryBuilder;
import javax.money.CurrencyUnit;
import javax.money.Monetary;
import javax.money.MonetaryAmount;
import javax.money.format.MonetaryFormats;
import org.javamoney.moneta.FastMoney;
public class TestCurrencyQuery {
public static void main(String[] args) {
System.out.println(System.getProperty("java.vm.name"));
System.out.println(System.getProperty("java.version"));
System.out.println(System.getProperty("java.specification.vendor"));
CurrencyQuery query = CurrencyQueryBuilder.of().setNumericCodes(840).build();
CurrencyUnit cu = Monetary.getCurrency(query);
MonetaryAmount amount = FastMoney.of(99.99, cu);
System.out.println(MonetaryFormats.getAmountFormat(Locale.ENGLISH).format(amount));
}
}
的pom.xml :
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>test</groupId>
<artifactId>test-jsr354</artifactId>
<version>0.0.1-SNAPSHOT</version>
<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
</properties>
<dependencies>
<dependency>
<groupId>org.javamoney</groupId>
<artifactId>moneta</artifactId>
<version>1.1</version>
</dependency>
</dependencies>
</project>
控制台输出:
Java HotSpot(TM) 64-Bit Server VM
1.8.0_31
Oracle Corporation
Exception in thread "main" javax.money.MonetaryException: Ambiguous request for CurrencyUnit: CurrencyQuery (
{Query.numericCodes=[840]}), found: [KHR, RON, XTS, FJD, LRD, MVR, BRL, ZMK, PKR, LBP, LYD, SDG, MXV, AED, XDR, STD, CDF, QAR, ISK, SHP, CSD, FRF, BMD, PTE, PLN, XUA, UYU, GYD, LAK, ZAR, ZMW, MKD, XSU, XAF, EEK, ILS, UGX, ITL, XPT, ROL, MUR, INR, TWD, KES, FIM, CHF, HNL, ARS, BGL, KRW, SBD, PHP, RUR, PYG, SRD, AWG, MXN, MGA, SGD, TRL, MZN, SOS, MOP, XBA, IRR, CZK, XFU, TRY, UZS, XFO, TTD, SDD, SCR, COP, ALL, XAU, SYP, USN, PAB, CUC, JMD, GNF, BHD, ANG, IDR, GWP, DEM, SLL, SVC, HRK, NLG, TMT, KZT, MTL, CUP, VEF, ZWN, NOK, LVL, CLF, TMM, BEF, VEB, MZM, DOP, GHS, BBD, XPF, CYP, UAH, BAM, TPE, BND, BYB, MGF, SIT, BWP, XBD, XCD, LSL, AYM, RUB, ADP, SEK, YUM, AOA, WST, GBP, ZWD, THB, ZWL, ESP, MAD, USS, ETB, NGN, AUD, TZS, XAG, VND, BTN, JOD, PGK, XBB, DKK, VUV, BYR, NZD, EGP, SSP, KMF, CNY, MWK, AZM, SAR, CVE, HUF, HTG, SRG, AZN, GIP, LUF, DJF, GEL, RWF, TJS, TOP, TND, ERN, OMR, GRD, MMK, LKR, FKP, NIO, ATS, KPW, PEN, AMD, IEP, BZD, XXX, BIF, GTQ, KYD, EUR, LTL, CRC, HKD, BGN, RSD, SZL, USD, KWD, CLP, MYR, BOB, AFA, GHC, JPY, AFN, GMD, MDL, IQD, BSD, MNT, NPR, MRO, XPD, DZD, NAD, CAD, BOV, KGS, ZWR, SKK, XOF, YER, BDT, XBC]
at javax.money.spi.MonetaryCurrenciesSingletonSpi.getCurrency(MonetaryCurrenciesSingletonSpi.java:173)
at javax.money.Monetary.getCurrency(Monetary.java:506)
at test.TestCurrencyQuery.main(TestCurrencyQuery.java:21)
答案 0 :(得分:1)
根据moneta的注释,货币只能通过货币代码或区域设置访问。此实现不提供按数字代码访问。以下是按货币代码USD:
访问的方法CurrencyQuery query = CurrencyQueryBuilder.of().setCurrencyCodes("USD").build();
CurrencyUnit cu = Monetary.getCurrency(query);
MonetaryAmount amount = FastMoney.of(99.99, cu);
System.out.println(MonetaryFormats.getAmountFormat(Locale.ENGLISH).format(amount));
如果您想根据数字代码提交查询,我建议您与项目本身联系。
或者,您可以使用getCurrencies()
检索所有货币,并根据数字代码进行过滤:
CurrencyUnit cu = Monetary.getCurrencies().stream()
.filter(c -> c.getNumericCode() == 840)
.findAny()
.orElseThrow(RuntimeException::new);
最后,你可以implement your own CurrencyProvider实现getCurrency基于数字代码进行搜索。
答案 1 :(得分:0)
如前所述,您无法使用此实现通过货币代码访问CurrencyUnit。 如果您的任务严格接受货币代码作为参数,则可以创建自己的映射。更好的方法是使用数据库,您可以在其中存储数字代码和货币代码之间的映射。
package test;
import java.util.Locale;
import javax.money.CurrencyQuery;
import javax.money.CurrencyQueryBuilder;
import javax.money.CurrencyUnit;
import javax.money.Monetary;
import javax.money.MonetaryAmount;
import javax.money.format.MonetaryFormats;
import org.javamoney.moneta.FastMoney;
public class TestCurrencyQuery {
public static void main(String[] args) {
System.out.println(System.getProperty("java.vm.name"));
System.out.println(System.getProperty("java.version"));
System.out.println(System.getProperty("java.specification.vendor"));
CurrencyQuery query = CurrencyQueryBuilder.of().setCurrencyCodes(getCurrencyCodesFromNumeric(840)).build();
CurrencyUnit cu = Monetary.getCurrency(query);
MonetaryAmount amount = FastMoney.of(99.99, cu);
System.out.println(MonetaryFormats.getAmountFormat(Locale.ENGLISH).format(amount));
}
public String[] getCurrencyCodesFromNumeric(int... codes) {
Collection<String> currencyCodes = // query db and return associated String currency codes;
return currencyCodes.toArray(new String[currencyCodes.size()]);
}
}