mirror of https://github.com/nodejs/node.git
buffer: check logic simplification
Checks have been simplified and optimized for most-used cases. Calling Buffer with another Buffer as the subject will now use the SlowBuffer Copy method instead of the for loop. No need to call for value coercion, just place the ternary inline.
This commit is contained in:
parent
053e02ef8e
commit
d69a26b965
|
@ -30,7 +30,7 @@ SlowBuffer.prototype.__proto__ = Buffer.prototype;
|
|||
|
||||
|
||||
function clamp(index, len, defaultValue) {
|
||||
if (typeof index === 'undefined') return defaultValue;
|
||||
if (typeof index !== 'number') return defaultValue;
|
||||
index = ~~index; // Coerce to integer.
|
||||
if (index >= len) return len;
|
||||
if (index >= 0) return index;
|
||||
|
@ -49,7 +49,7 @@ function toHex(n) {
|
|||
SlowBuffer.prototype.toString = function(encoding, start, end) {
|
||||
encoding = String(encoding || 'utf8').toLowerCase();
|
||||
start = +start || 0;
|
||||
if (typeof end == 'undefined') end = this.length;
|
||||
if (typeof end !== 'number') end = this.length;
|
||||
|
||||
// Fastpath empty strings
|
||||
if (+end == start) {
|
||||
|
@ -150,15 +150,6 @@ SlowBuffer.prototype.slice = function(start, end) {
|
|||
};
|
||||
|
||||
|
||||
function coerce(length) {
|
||||
// Coerce length to a number (possibly NaN), round up
|
||||
// in case it's fractional (e.g. 123.456). Since NaN
|
||||
// comparisons are always false, use to return zero.
|
||||
length = Math.ceil(+length);
|
||||
return length > 0 ? length : 0;
|
||||
}
|
||||
|
||||
|
||||
var zeroBuffer = new SlowBuffer(0);
|
||||
|
||||
// Buffer
|
||||
|
@ -175,22 +166,22 @@ function Buffer(subject, encoding, offset) {
|
|||
throw new TypeError('First argument must be a Buffer when slicing');
|
||||
}
|
||||
|
||||
this.length = coerce(encoding);
|
||||
this.length = +encoding > 0 ? Math.ceil(encoding) : 0;
|
||||
this.parent = subject.parent ? subject.parent : subject;
|
||||
this.offset = offset;
|
||||
} else {
|
||||
// Find the length
|
||||
switch (type = typeof subject) {
|
||||
case 'number':
|
||||
this.length = coerce(subject);
|
||||
this.length = +subject > 0 ? Math.ceil(subject) : 0;
|
||||
break;
|
||||
|
||||
case 'string':
|
||||
this.length = Buffer.byteLength(subject, encoding);
|
||||
break;
|
||||
|
||||
case 'object': // Assume object is an array
|
||||
this.length = coerce(subject.length);
|
||||
case 'object': // Assume object is array-ish
|
||||
this.length = +subject.length > 0 ? Math.ceil(subject.length) : 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
|
@ -217,14 +208,24 @@ function Buffer(subject, encoding, offset) {
|
|||
this.offset = 0;
|
||||
}
|
||||
|
||||
// Treat array-ish objects as a byte array.
|
||||
if (isArrayIsh(subject)) {
|
||||
for (var i = 0; i < this.length; i++) {
|
||||
this.parent[i + this.offset] = subject[i];
|
||||
// optimize by branching logic for new allocations
|
||||
if (typeof subject !== 'number') {
|
||||
if (type === 'string') {
|
||||
// We are a string
|
||||
this.length = this.write(subject, 0, encoding);
|
||||
// if subject is buffer then use built-in copy method
|
||||
} else if (Buffer.isBuffer(subject)) {
|
||||
if (subject.parent)
|
||||
subject.parent.copy(this.parent,
|
||||
this.offset,
|
||||
subject.offset,
|
||||
this.length + subject.offset);
|
||||
else
|
||||
subject.copy(this.parent, this.offset, 0, this.length);
|
||||
} else if (isArrayIsh(subject)) {
|
||||
for (var i = 0; i < this.length; i++)
|
||||
this.parent[i + this.offset] = subject[i];
|
||||
}
|
||||
} else if (type == 'string') {
|
||||
// We are a string
|
||||
this.length = this.write(subject, 0, encoding);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -232,7 +233,7 @@ function Buffer(subject, encoding, offset) {
|
|||
}
|
||||
|
||||
function isArrayIsh(subject) {
|
||||
return Array.isArray(subject) || Buffer.isBuffer(subject) ||
|
||||
return Array.isArray(subject) ||
|
||||
subject && typeof subject === 'object' &&
|
||||
typeof subject.length === 'number';
|
||||
}
|
||||
|
@ -388,13 +389,13 @@ Buffer.prototype.toJSON = function() {
|
|||
Buffer.prototype.toString = function(encoding, start, end) {
|
||||
encoding = String(encoding || 'utf8').toLowerCase();
|
||||
|
||||
if (typeof start == 'undefined' || start < 0) {
|
||||
if (typeof start !== 'number' || start < 0) {
|
||||
start = 0;
|
||||
} else if (start > this.length) {
|
||||
start = this.length;
|
||||
}
|
||||
|
||||
if (typeof end == 'undefined' || end > this.length) {
|
||||
if (typeof end !== 'number' || end > this.length) {
|
||||
end = this.length;
|
||||
} else if (end < 0) {
|
||||
end = 0;
|
||||
|
@ -445,7 +446,7 @@ Buffer.prototype.fill = function fill(value, start, end) {
|
|||
if (typeof value === 'string') {
|
||||
value = value.charCodeAt(0);
|
||||
}
|
||||
if (!(typeof value === 'number') || isNaN(value)) {
|
||||
if (typeof value !== 'number' || isNaN(value)) {
|
||||
throw new TypeError('value is not a number');
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue