The Javascript splice
only works with arrays. Is there similar method for strings? Or should I create my own custom function?
The substr()
,
There seem to be a lot of confusion which was addressed only in comments by elclanrs and raina77ow, so let me post a clarifying answer.
From "string.splice
" one may expect that it, like the one for arrays:
The problem is, the 3d requirement can not be fulfilled because strings are immutable (related: 1, 2), I've found the most dedicated comment here:
In JavaScript strings are primitive value types and not objects (spec). In fact, as of ES5, they're one of the only 5 value types alongside
null
,undefined
,number
andboolean
. Strings are assigned by value and not by reference and are passed as such. Thus, strings are not just immutable, they are a value. Changing the string"hello"
to be"world"
is like deciding that from now on the number 3 is the number 4... it makes no sense.
So, with that in account, one may expect the "string.splice
" thing to only:
which is what substr
does; or, alternatively,
which is the subject of the next section.
If you care about optimizing, you should probably use the Mike's implementation:
String.prototype.splice = function(index, count, add) {
if (index < 0) {
index += this.length;
if (index < 0)
index = 0;
}
return this.slice(0, index) + (add || "") + this.slice(index + count);
}
Treating the out-of-boundaries index may vary, though. Depending on your needs, you may want:
if (index < 0) {
index += this.length;
if (index < 0)
index = 0;
}
if (index >= this.length) {
index -= this.length;
if (index >= this.length)
index = this.length - 1;
}
or even
index = index % this.length;
if (index < 0)
index = this.length + index;
If you don't care about performance, you may want to adapt Kumar's suggestion which is more straight-forward:
String.prototype.splice = function(index, count, add) {
var chars = this.split('');
chars.splice(index, count, add);
return chars.join('');
}
The difference in performances increases drastically with the length of the string. jsperf shows, that for strings with the length of 10 the latter solution (splitting & joining) is twice slower than the former solution (using slice), for 100-letter strings it's x5 and for 1000-letter strings it's x50, in Ops/sec it's:
10 letters 100 letters 1000 letters
slice implementation 1.25 M 2.00 M 1.91 M
split implementation 0.63 M 0.22 M 0.04 M
note that I've changed the 1st and 2d arguments when moving from 10 letters to 100 letters (still I'm surprised that the test for 100 letters runs faster than that for 10 letters).
Louis's spliceSlice method fails when add value is 0 or other falsy values, here is a fix:
function spliceSlice(str, index, count, add) {
if (index < 0) {
index = str.length + index;
if (index < 0) {
index = 0;
}
}
const hasAdd = typeof add !== 'undefined';
return str.slice(0, index) + (hasAdd ? add : '') + str.slice(index + count);
}
I solved my problem using this code, is a somewhat replacement for the missing splice.
let str = "I need to remove a character from this";
let pos = str.indexOf("character")
if(pos>-1){
let result = str.slice(0, pos-2) + str.slice(pos, str.length);
console.log(result) //I need to remove character from this
}
I needed to remove a character before/after a certain word, after you get the position the string is split in two and then recomposed by flexibly removing characters using an offset along pos
I would like to offer a simpler alternative to both the Kumar/Cody and the Louis methods. On all the tests I ran, it performs as fast as the Louis method (see fiddle tests for benchmarks).
String.prototype.splice = function(startIndex,length,insertString){
return this.substring(0,startIndex) + insertString + this.substring(startIndex + length);
};
You can use it like this:
var creditCardNumber = "5500000000000004";
var cardSuffix = creditCardNumber.splice(0,12,'****');
console.log(cardSuffix); // output: ****0004
See Test Results: https://jsfiddle.net/0quz9q9m/5/
So, whatever adding splice method to a String prototype cant work transparent to spec...
String.prototype.splice = function(...a){
for(var r = '', p = 0, i = 1; i < a.length; i+=3)
r+= this.slice(p, p=a[i-1]) + (a[i+1]||'') + this.slice(p+a[i], p=a[i+2]||this.length);
return r;
}
This is of course not the best way to "splice" a string, I had given this as an example of how the implementation would be, which is flawed and very evident from a split(), splice() and join(). For a far better implementation, see Louis's method.
No, there is no such thing as a String.splice
, but you can try this:
newStr = str.split(''); // or newStr = [...str];
newStr.splice(2,5);
newStr = newStr.join('');
I realise there is no splice
function as in Arrays, so you have to convert the string into an array. Hard luck...