ICU-11276 Adding more test cases. Fixing minor issues with extended locales.

This commit is contained in:
Shane Carr 2018-09-14 21:20:13 -07:00
parent 39fa9d9192
commit 432f7ecc95
4 changed files with 121 additions and 6 deletions

View file

@ -11,6 +11,7 @@
#include "unicode/numberrangeformatter.h"
#include "numrange_impl.h"
#include "patternprops.h"
#include "uresimp.h"
#include "util.h"
@ -207,6 +208,9 @@ void NumberRangeFormatterImpl::format(UFormattedNumberRangeData& data, bool equa
} else {
formatterImpl2.preProcess(data.quantity2, micros2, status);
}
if (U_FAILURE(status)) {
return;
}
// If any of the affixes are different, an identity is not possible
// and we must use formatRange().
@ -392,18 +396,25 @@ void NumberRangeFormatterImpl::formatRange(UFormattedNumberRangeData& data,
status);
if (U_FAILURE(status)) { return; }
lengthInfix = lengthRange - lengthPrefix - lengthSuffix;
U_ASSERT(lengthInfix > 0);
// SPACING HEURISTIC
// Add spacing unless all modifiers are collapsed.
// TODO: add API to control this?
// TODO: Use a data-driven heuristic like currency spacing?
// TODO: Use Unicode [:whitespace:] instead of PatternProps whitespace? (consider speed implications)
{
bool repeatInner = !collapseInner && micros1.modInner->getCodePointCount() > 0;
bool repeatMiddle = !collapseMiddle && micros1.modMiddle->getCodePointCount() > 0;
bool repeatOuter = !collapseOuter && micros1.modOuter->getCodePointCount() > 0;
if (repeatInner || repeatMiddle || repeatOuter) {
// Add spacing
lengthInfix += string.insertCodePoint(UPRV_INDEX_1, u'\u0020', UNUM_FIELD_COUNT, status);
lengthInfix += string.insertCodePoint(UPRV_INDEX_2, u'\u0020', UNUM_FIELD_COUNT, status);
// Add spacing if there is not already spacing
if (!PatternProps::isWhiteSpace(string.charAt(UPRV_INDEX_1))) {
lengthInfix += string.insertCodePoint(UPRV_INDEX_1, u'\u0020', UNUM_FIELD_COUNT, status);
}
if (!PatternProps::isWhiteSpace(string.charAt(UPRV_INDEX_2 - 1))) {
lengthInfix += string.insertCodePoint(UPRV_INDEX_2, u'\u0020', UNUM_FIELD_COUNT, status);
}
}
}

View file

@ -141,6 +141,54 @@ void NumberRangeFormatterTest::testBasic() {
u"~5 000 degrés Fahrenheit",
u"5 0005 000 000 degrés Fahrenheit");
assertFormatRange(
u"Locale with custom range separator",
NumberRangeFormatter::with(),
Locale("ja"),
u"15",
u"~5",
u"~5",
u"03",
u"~0",
u"33,000",
u"3,0005,000",
u"4,9995,001",
u"~5,000",
u"5,0005,000,000");
assertFormatRange(
u"Locale that already has spaces around range separator",
NumberRangeFormatter::with()
.collapse(UNUM_RANGE_COLLAPSE_NONE)
.numberFormatterBoth(NumberFormatter::with().unit(KELVIN)),
Locale("hr"),
u"1 K 5 K",
u"~5 K",
u"~5 K",
u"0 K 3 K",
u"~0 K",
u"3 K 3.000 K",
u"3.000 K 5.000 K",
u"4.999 K 5.001 K",
u"~5.000 K",
u"5.000 K 5.000.000 K");
assertFormatRange(
u"Locale with custom numbering system and no plural ranges data",
NumberRangeFormatter::with(),
Locale("shn@numbers=beng"),
// 012459 = ০১৩৪৫৯
u"১–৫",
u"~৫",
u"~৫",
u"০–৩",
u"~",
u"৩–৩,",
u"৩,০০০–৫,",
u",৯৯৯–৫,০০১",
u"~৫,",
u"৫,০০০–৫,,");
assertFormatRange(
u"Portuguese currency",
NumberRangeFormatter::with()

View file

@ -4,6 +4,7 @@ package com.ibm.icu.number;
import com.ibm.icu.impl.ICUData;
import com.ibm.icu.impl.ICUResourceBundle;
import com.ibm.icu.impl.PatternProps;
import com.ibm.icu.impl.SimpleFormatterImpl;
import com.ibm.icu.impl.StandardPlural;
import com.ibm.icu.impl.UResource;
@ -287,18 +288,25 @@ class NumberRangeFormatterImpl {
PrefixInfixSuffixLengthHelper h = new PrefixInfixSuffixLengthHelper();
SimpleModifier.formatTwoArgPattern(fRangePattern, string, 0, h, null);
assert h.lengthInfix > 0;
// SPACING HEURISTIC
// Add spacing unless all modifiers are collapsed.
// TODO: add API to control this?
// TODO: Use a data-driven heuristic like currency spacing?
// TODO: Use Unicode [:whitespace:] instead of PatternProps whitespace? (consider speed implications)
{
boolean repeatInner = !collapseInner && micros1.modInner.getCodePointCount() > 0;
boolean repeatMiddle = !collapseMiddle && micros1.modMiddle.getCodePointCount() > 0;
boolean repeatOuter = !collapseOuter && micros1.modOuter.getCodePointCount() > 0;
if (repeatInner || repeatMiddle || repeatOuter) {
// Add spacing
h.lengthInfix += string.insertCodePoint(h.index1(), '\u0020', null);
h.lengthInfix += string.insertCodePoint(h.index2(), '\u0020', null);
// Add spacing if there is not already spacing
if (!PatternProps.isWhiteSpace(string.charAt(h.index1()))) {
h.lengthInfix += string.insertCodePoint(h.index1(), '\u0020', null);
}
if (!PatternProps.isWhiteSpace(string.charAt(h.index2() - 1))) {
h.lengthInfix += string.insertCodePoint(h.index2(), '\u0020', null);
}
}
}

View file

@ -129,6 +129,54 @@ public class NumberRangeFormatterTest {
"~5 000 degrés Fahrenheit",
"5 0005 000 000 degrés Fahrenheit");
assertFormatRange(
"Locale with custom range separator",
NumberRangeFormatter.with(),
new ULocale("ja"),
"15",
"~5",
"~5",
"03",
"~0",
"33,000",
"3,0005,000",
"4,9995,001",
"~5,000",
"5,0005,000,000");
assertFormatRange(
"Locale that already has spaces around range separator",
NumberRangeFormatter.with()
.collapse(RangeCollapse.NONE)
.numberFormatterBoth(NumberFormatter.with().unit(MeasureUnit.KELVIN)),
new ULocale("hr"),
"1 K 5 K",
"~5 K",
"~5 K",
"0 K 3 K",
"~0 K",
"3 K 3.000 K",
"3.000 K 5.000 K",
"4.999 K 5.001 K",
"~5.000 K",
"5.000 K 5.000.000 K");
assertFormatRange(
"Locale with custom numbering system and no plural ranges data",
NumberRangeFormatter.with(),
new ULocale("shn@numbers=beng"),
// 012459 = ০১৩৪৫৯
"১–৫",
"~৫",
"~৫",
"০–৩",
"~",
"৩–৩,",
"৩,০০০–৫,",
",৯৯৯–৫,০০১",
"~৫,",
"৫,০০০–৫,,");
assertFormatRange(
"Portuguese currency",
NumberRangeFormatter.with()