Skip to content

Commit

Permalink
fix: correctly interpret digits followed by multiple powers of ten
Browse files Browse the repository at this point in the history
Fixes #1399.
  • Loading branch information
birtles committed May 29, 2024
1 parent 2616086 commit fc221c1
Show file tree
Hide file tree
Showing 3 changed files with 38 additions and 12 deletions.
9 changes: 7 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,16 @@ app.

## [Unreleased]

- Changed puck behavior to no longer hold the popup window like a regular
mouse event would ([#1767](https://github.com/birchill/10ten-ja-reader/discussions/1767)).
- Made it possible to change tabs in the popup by swiping horizontally
thanks to [@StarScape](https://github.com/StarScape)
([#1656](https://github.com/birchill/10ten-ja-reader/issues/1656)).
- Bundled fonts used by the popup to provide consistent display and avoid issues
with sites that patch system fonts
([#1560](https://github.com/birchill/10ten-ja-reader/issues/1560)).
- Changed puck behavior to no longer hold the popup window like a regular
mouse event would
thanks to [@StarScape](https://github.com/StarScape)
([#1767](https://github.com/birchill/10ten-ja-reader/discussions/1767)).
- Made copying to the clipboard include rare headwords again when not using
simplified copy mode
([#1665](https://github.com/birchill/10ten-ja-reader/issues/1665)).
Expand All @@ -34,6 +36,9 @@ app.
([#1677](https://github.com/birchill/10ten-ja-reader/issues/1677)).
- Made senses no longer be restricted when matching on search-only headwords
([#1551](https://github.com/birchill/10ten-ja-reader/issues/1551)).
- Fixed translation of odd numbers with digits and multiple powers of ten like
11,786百万円
([#1399](https://github.com/birchill/10ten-ja-reader/issues/1399)).

## [1.18.0] - 2024-02-26

Expand Down
3 changes: 3 additions & 0 deletions src/content/numbers.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,9 @@ describe('parseNumber', () => {
expect(parseNumber('1.2億')).toEqual(120000000);
// As seen here: https://www.athome.co.jp/kodate/1008941087/
expect(parseNumber('39,800万')).toEqual(398_000_000);
// https://github.com/birchill/10ten-ja-reader/issues/1399
expect(parseNumber('11,786百万')).toEqual(11_786_000_000);
expect(parseNumber('123,456,789百万')).toEqual(123_456_789_000_000);

// Bogus inputs

Expand Down
38 changes: 28 additions & 10 deletions src/content/numbers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -111,16 +111,14 @@ export function parseNumber(inputText: string): number | null {
let numbers = digits as Array<number>;

// Special case where we have a series of digits followed by a power of ten,
// e.g. 39,800万円. These don't follow the usual rules of numbers so we treat
// them separately.
if (
numbers.length > 1 &&
numbers.slice(0, -1).every((d) => d >= 0 && d < 10) &&
numbers[numbers.length - 1]! >= 100
) {
const powerOfTen = numbers.pop()!;
const multiplier = numbers.reduce((acc, d) => acc * 10 + d, 0);
return multiplier * powerOfTen;
// e.g. 39,800万円 and 11,786百万. These don't follow the usual rules of
// numbers so we treat them separately.
const digitsAndPowersOfTen = getDigitsAndPowersOfTen(numbers);
if (digitsAndPowersOfTen) {
const [digits, powersOfTen] = digitsAndPowersOfTen;
const multiplier = digits.reduce((acc, d) => acc * 10 + d, 0);
const base = powersOfTen.reduce((acc, p) => acc * p, 1);
return multiplier * base;
}

let result = 0;
Expand Down Expand Up @@ -173,6 +171,26 @@ export function parseNumber(inputText: string): number | null {
return result + (numbers.length ? numbers[0] : 0);
}

function getDigitsAndPowersOfTen(
arr: Array<number>
): [Array<number>, Array<number>] | null {
let lastPowerOfTen = arr.length;
while (lastPowerOfTen && arr[lastPowerOfTen - 1] >= 100) {
--lastPowerOfTen;
}

if (lastPowerOfTen === 0 || lastPowerOfTen === arr.length) {
return null;
}

const digits = arr.slice(0, lastPowerOfTen);
if (!digits.every((d) => d >= 0 && d < 10)) {
return null;
}

return [digits, arr.slice(lastPowerOfTen)];
}

function validSequence(c1: number, c2: number): boolean {
// If we have xxx万, xxx億, xxx兆 then the only requirement is that xxx is less
// than the 'base'.
Expand Down

0 comments on commit fc221c1

Please sign in to comment.