Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,6 @@

// MODULES //

var isNumber = require( './is_number.js' );

// NOTE: for the following, we explicitly avoid using stdlib packages in this particular package in order to avoid circular dependencies.
var abs = Math.abs; // eslint-disable-line stdlib/no-builtin-math
var lowercase = String.prototype.toLowerCase;
Expand All @@ -46,21 +44,15 @@ var RE_ZERO_BEFORE_EXP = /(\..*[^0])0*e/;
* Formats a token object argument as a floating-point number.
*
* @private
* @param {number} f - parsed number
* @param {Object} token - token object
* @throws {Error} must provide a valid floating-point number
* @returns {string} formatted token argument
*/
function formatDouble( token ) {
function formatDouble( f, token ) {
var digits;
var out;
var f = parseFloat( token.arg );
if ( !isFinite( f ) ) { // NOTE: We use the global `isFinite` function here instead of `@stdlib/math/base/assert/is-finite` in order to avoid circular dependencies.
if ( !isNumber( token.arg ) ) {
throw new Error( 'invalid floating-point number. Value: ' + out );
}
// Case: NaN, Infinity, or -Infinity
f = token.arg;
}

switch ( token.specifier ) {
case 'e':
case 'E':
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@

var formatInteger = require( './format_integer.js' );
var isString = require( './is_string.js' );
var isNumber = require( './is_number.js' );
var formatDouble = require( './format_double.js' );
var spacePad = require( './space_pad.js' );
var zeroPad = require( './zero_pad.js' );
Expand Down Expand Up @@ -96,6 +97,7 @@ function formatInterpolate( tokens ) {
var num;
var out;
var pos;
var f;
var i;
var j;

Expand Down Expand Up @@ -205,7 +207,16 @@ function formatInterpolate( tokens ) {
if ( !hasPeriod ) {
token.precision = 6;
}
token.arg = formatDouble( token );
f = parseFloat( token.arg );
if ( !isFinite( f ) ) { // NOTE: We use the global `isFinite` function here instead of `@stdlib/math/base/assert/is-finite` in order to avoid circular dependencies.
if ( !isNumber( token.arg ) ) {
throw new Error( 'invalid floating-point number. Value: ' + out );
}
// Case: NaN, Infinity, or -Infinity
f = token.arg;
token.padZeros = false;
}
token.arg = formatDouble( f, token );
break;
default:
throw new Error( 'invalid specifier: ' + token.specifier );
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,7 @@ tape( 'the function returns a double-formatted token argument', function test( t
'precision': 2
};
expected = '3.14';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

token = {
Expand All @@ -53,7 +53,7 @@ tape( 'the function returns a double-formatted token argument', function test( t
'precision': 4
};
expected = '3.1416';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

token = {
Expand All @@ -62,7 +62,7 @@ tape( 'the function returns a double-formatted token argument', function test( t
'precision': 2
};
expected = '3.14e+00';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

token = {
Expand All @@ -71,7 +71,7 @@ tape( 'the function returns a double-formatted token argument', function test( t
'precision': 2
};
expected = '3.14E+00';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

t.end();
Expand All @@ -89,7 +89,7 @@ tape( 'the function returns a double-formatted token argument (include sign)', f
'sign': '+'
};
expected = '+3.14';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

token = {
Expand All @@ -99,7 +99,7 @@ tape( 'the function returns a double-formatted token argument (include sign)', f
'sign': '-'
};
expected = '-3.1416';
actual = formatDouble( token );
actual = formatDouble( PI, token );
t.strictEqual( actual, expected, 'returns expected value' );

t.end();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -625,6 +625,30 @@
expected = 'beep 5.000';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%.10f %.10f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, PINF, NINF );
expected = 'infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%0.10f %0.10f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, PINF, NINF );
expected = 'infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%.4f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, NaN );
expected = 'nan';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%0.4f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, NaN );
expected = 'nan';
t.strictEqual( actual, expected, 'returns expected output' );

Comment on lines +628 to +651
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think these are probably the most relevant ones related to the fix. If the other tests below are not needed, I can remove them.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reason for choosing %0.10f for infinity and -infinity is that -infinity is 9 characters long, and using a precision of 10 can correctly check for no zero-padding. The same reasoning applies to NaN and 0.4f.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That makes sense.

t.end();
});

Expand Down Expand Up @@ -652,6 +676,30 @@
expected = '3.142 3.142 baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%.*f %.*f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, 10, PINF, 10, NINF );
expected = 'infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%0.*f %0.*f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, 10, PINF, 10, NINF );
expected = 'infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%.*f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, 4, NaN );
expected = 'nan';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%0.*f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, 4, NaN );
expected = 'nan';
t.strictEqual( actual, expected, 'returns expected output' );

t.end();
});

Expand Down Expand Up @@ -820,6 +868,18 @@
expected = ' 3.140 5.000 baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%10.10f %10.10f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, PINF, NINF );
expected = ' infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%8.4f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, NaN );
expected = ' nan';
t.strictEqual( actual, expected, 'returns expected output' );

t.end();
});

Expand Down Expand Up @@ -847,6 +907,18 @@
expected = '3.140 5.000 baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%-10.10f %10.10f baz';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, PINF, NINF );
expected = 'infinity -infinity baz';
t.strictEqual( actual, expected, 'returns expected output' );

str = '%-8.4f';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, NaN );
expected = 'nan ';
t.strictEqual( actual, expected, 'returns expected output' );

t.end();
});

Expand Down Expand Up @@ -1171,7 +1243,7 @@
str = 'beep %e';
tokens = formatTokenize( str );
actual = formatInterpolate( tokens, -5 );
expected = 'beep -5.000000e+00';

Check warning on line 1246 in lib/node_modules/@stdlib/string/base/format-interpolate/test/test.js

View workflow job for this annotation

GitHub Actions / Lint Changed Files

File has too many lines (1097). Maximum allowed is 1000
t.strictEqual( actual, expected, 'returns expected output' );

str = '%e %e baz';
Expand Down