Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Treat null as undefined. #241

Merged
merged 4 commits into from Mar 29, 2021
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.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/continuous.js
Expand Up @@ -83,7 +83,7 @@ export function transformer() {
}

function scale(x) {
return isNaN(x = +x) ? unknown : (output || (output = piecewise(domain.map(transform), range, interpolate)))(transform(clamp(x)));
return x == null || isNaN(x = +x) ? unknown : (output || (output = piecewise(domain.map(transform), range, interpolate)))(transform(clamp(x)));
}

scale.invert = function(y) {
Expand Down
2 changes: 1 addition & 1 deletion src/identity.js
Expand Up @@ -5,7 +5,7 @@ export default function identity(domain) {
var unknown;

function scale(x) {
return isNaN(x = +x) ? unknown : x;
return x == null || isNaN(x = +x) ? unknown : x;
}

scale.invert = scale;
Expand Down
2 changes: 1 addition & 1 deletion src/quantile.js
Expand Up @@ -15,7 +15,7 @@ export default function quantile() {
}

function scale(x) {
return isNaN(x = +x) ? unknown : range[bisect(thresholds, x)];
return x == null || isNaN(x = +x) ? unknown : range[bisect(thresholds, x)];
}

scale.invertExtent = function(y) {
Expand Down
2 changes: 1 addition & 1 deletion src/quantize.js
Expand Up @@ -11,7 +11,7 @@ export default function quantize() {
unknown;

function scale(x) {
return x <= x ? range[bisect(domain, x, 0, n)] : unknown;
return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown;
}

function rescale() {
Expand Down
2 changes: 1 addition & 1 deletion src/sequential.js
Expand Up @@ -18,7 +18,7 @@ function transformer() {
unknown;

function scale(x) {
return isNaN(x = +x) ? unknown : interpolator(k10 === 0 ? 0.5 : (x = (transform(x) - t0) * k10, clamp ? Math.max(0, Math.min(1, x)) : x));
return x == null || isNaN(x = +x) ? unknown : interpolator(k10 === 0 ? 0.5 : (x = (transform(x) - t0) * k10, clamp ? Math.max(0, Math.min(1, x)) : x));
}

scale.domain = function(_) {
Expand Down
2 changes: 1 addition & 1 deletion src/sequentialQuantile.js
Expand Up @@ -7,7 +7,7 @@ export default function sequentialQuantile() {
interpolator = identity;

function scale(x) {
if (!isNaN(x = +x)) return interpolator((bisect(domain, x, 1) - 1) / (domain.length - 1));
if (x != null && !isNaN(x = +x)) return interpolator((bisect(domain, x, 1) - 1) / (domain.length - 1));
}

scale.domain = function(_) {
Expand Down
2 changes: 1 addition & 1 deletion src/threshold.js
Expand Up @@ -8,7 +8,7 @@ export default function threshold() {
n = 1;

function scale(x) {
return x <= x ? range[bisect(domain, x, 0, n)] : unknown;
return x != null && x <= x ? range[bisect(domain, x, 0, n)] : unknown;
}

scale.domain = function(_) {
Expand Down
10 changes: 10 additions & 0 deletions test/identity-test.js
Expand Up @@ -31,6 +31,16 @@ tape("identity(x) coerces input to a number", function(test) {
test.end();
});

tape("identity(undefined) returns unknown", function(test) {
var s = scale.scaleIdentity().unknown(-1);
test.equal(s(undefined), -1);
test.equal(s(null), -1);
test.equal(s(NaN), -1);
test.equal(s("N/A"), -1);
test.equal(s(0.4), 0.4);
test.end();
});

tape("identity.invert(y) is the identity function", function(test) {
var s = scale.scaleIdentity().domain([1, 2]);
test.equal(s.invert(0.5), 0.5);
Expand Down
7 changes: 2 additions & 5 deletions test/linear-test.js
Expand Up @@ -209,8 +209,9 @@ tape("linear.rangeRound(range) accepts an iterable", function(test) {
test.end();
});

tape("linear.unknown(value) sets the return value for undefined and NaN input", function(test) {
tape("linear.unknown(value) sets the return value for undefined, null, and NaN input", function(test) {
var s = scale.scaleLinear().unknown(-1);
test.equal(s(null), -1);
test.equal(s(undefined), -1);
test.equal(s(NaN), -1);
test.equal(s("N/A"), -1);
Expand Down Expand Up @@ -388,15 +389,12 @@ tape("linear.ticks(X) spans linear.nice(X).domain()", function(test) {
var ticks = s.ticks(count);
test.deepEqual([ticks[0], ticks[ticks.length - 1]], s.domain());
}

check([1, 9], 2);
check([1, 9], 3);
check([1, 9], 4);

check([8, 9], 2);
check([8, 9], 3);
check([8, 9], 4);

check([1, 21], 2);
check([2, 21], 2);
check([3, 21], 2);
Expand All @@ -408,7 +406,6 @@ tape("linear.ticks(X) spans linear.nice(X).domain()", function(test) {
check([9, 21], 2);
check([10, 21], 2);
check([11, 21], 2);

test.end();
})

Expand Down
3 changes: 2 additions & 1 deletion test/quantile-test.js
Expand Up @@ -129,9 +129,10 @@ tape("quantile.invertExtent() returns the first match if duplicate values exist
test.end();
});

tape("quantile.unknown(value) sets the return value for undefined and NaN input", function(test) {
tape("quantile.unknown(value) sets the return value for undefined, null, and NaN input", function(test) {
var s = scale.scaleQuantile().domain([3, 6, 7, 8, 8, 10, 13, 15, 16, 20]).range([0, 1, 2, 3]).unknown(-1);
test.equal(s(undefined), -1);
test.equal(s(null), -1);
test.equal(s(NaN), -1);
test.equal(s("N/A"), -1);
test.equal(s(2), 0);
Expand Down
8 changes: 8 additions & 0 deletions test/quantize-test.js
Expand Up @@ -36,6 +36,14 @@ tape("quantize(value) clamps input values to the domain", function(test) {
test.end();
});

tape("quantize.unknown(value) sets the return value for undefined, null, and NaN input", function(test) {
var s = scale.scaleQuantize().range([0, 1, 2]).unknown(-1);
test.equal(s(undefined), -1);
test.equal(s(null), -1);
test.equal(s(NaN), -1);
test.end();
});

tape("quantize.domain() coerces domain values to numbers", function(test) {
var s = scale.scaleQuantize().domain(["-1.20", "2.40"]);
test.deepEqual(s.domain(), [-1.2, 2.4]);
Expand Down
2 changes: 1 addition & 1 deletion test/threshold-test.js
Expand Up @@ -26,7 +26,7 @@ tape("threshold(x) returns undefined if the specified value x is not orderable",
test.equal(x(), undefined);
test.equal(x(undefined), undefined);
test.equal(x(NaN), undefined);
test.equal(x(null), "a"); // null < 1/3
test.equal(x(null), undefined);
test.end();
});

Expand Down