Javascript splice
działa tylko z tablicami. Czy istnieje podobna metoda dla stringów? A może powinienem utworzyć własną funkcję niestandardową?
Te substr()
i substring()
metody tylko zwrócić wyodrębniony i nie zmieniają oryginalnego łańcucha. To, co chcę zrobić, to usunąć część z mojego ciągu i zastosować zmianę do oryginalnego ciągu. Co więcej, metoda replace()
nie zadziała w moim przypadku, ponieważ chcę usunąć części zaczynające się od indeksu, a kończące na jakimś innym indeksie, dokładnie tak, jak mogę zrobić z splice()
metodą. Próbowałem przekonwertować mój ciąg na tablicę, ale nie jest to zgrabna metoda.
javascript
ProllyGeek
źródło
źródło
str.split
może to być funkcja, której szukasz: google.com/#q=javascript+string+splitstr = str.slice()
?return string.slice(0, startToSplice) + string.slice(endToSplice);
nie?Odpowiedzi:
Szybciej jest dwukrotnie przeciąć strunę, na przykład:
function spliceSlice(str, index, count, add) { // We cannot pass negative indexes directly to the 2nd slicing operation. if (index < 0) { index = str.length + index; if (index < 0) { index = 0; } } return str.slice(0, index) + (add || "") + str.slice(index + count); }
niż użycie podziału, po którym następuje złączenie (metoda Kumara Harsha), na przykład:
function spliceSplit(str, index, count, add) { var ar = str.split(''); ar.splice(index, count, add); return ar.join(''); }
Oto plik jsperf, który porównuje te dwie metody i kilka innych. (jsperf nie działa już od kilku miesięcy. Prosimy o sugerowanie alternatyw w komentarzach).
Chociaż powyższy kod implementuje funkcje, które odtwarzają ogólną funkcjonalność
splice
, optymalizacja kodu dla przypadku przedstawionego przez pytającego (to jest dodanie niczego do zmodyfikowanego ciągu) nie zmienia względnej wydajności różnych metod.źródło
String.prototype.splice = function (index, count, add) { return this.slice(0, index) + (add || "") + this.slice(index + count); }
Pamiętaj, że nie działa dokładnie tak samo jak metoda łączenia tablicy, ponieważ łańcuchy są niezmienne (nie możesz ich modyfikować po utworzeniu). Tak więc użycie byłoby następujące:var s="ss"; s = s.splice(0,1,"t");
var StringUtils={'StringSplice':/*func def*/};
byłby standardem do manipulacji napisami, ponieważ powiedziałeś, że jest niezmienny.Edytować
Nie jest to oczywiście najlepszy sposób na „łączenie” łańcucha, podałem to jako przykład tego, jak wyglądałaby implementacja, która jest wadliwa i bardzo widoczna w przypadku split (), splice () i join (). Aby uzyskać znacznie lepszą implementację, zobacz metodę Louisa .
Nie, nie ma czegoś takiego jak a
String.splice
, ale możesz spróbować tego:newStr = str.split(''); // or newStr = [...str]; newStr.splice(2,5); newStr = newStr.join('');
Zdaję sobie sprawę, że nie ma takiej
splice
funkcji jak w Arrays, więc musisz przekonwertować ciąg na tablicę. Pech ...źródło
"asdsd".indexOf('s');
[...str]
Oto ładne, małe curry, które zapewnia lepszą czytelność (IMHO):
Podpis drugiej funkcji jest identyczny z
Array.prototype.splice
metodą.function mutate(s) { return function splice() { var a = s.split(''); Array.prototype.splice.apply(a, arguments); return a.join(''); }; } mutate('101')(1, 1, '1');
Wiem, że jest już zaakceptowana odpowiedź, ale mam nadzieję, że jest przydatna.
źródło
'method'
parametr, dzięki czemu możesz przekazaćArray.prototype[method]
ciągi i traktować je całkowicie jak tablice. Również z tego samego jednego, można streszczenie rzeczywisty proces do innej funkcji - a jeśli nie ma ciąg, powrót funkcję, która będzie miała ciąg i odwrócić curry:mutate()(1, 1, '1')('101')
; Możesz nawet duckType argumenty, aby usunąć curry z pustego wywołania - a nawet hermetyzować samą metodę. Jeśli potrzebujesz tych rzeczy, możesz jednak zajrzeć do wzorca poleceń . Po prostu plujcie tutaj.Chciałbym zaoferować prostszą alternatywę zarówno dla metody Kumar / Cody, jak i metody Louisa. We wszystkich testach, które przeprowadziłem, działa tak szybko, jak metoda Louisa (patrz testy skrzypiec dla testów porównawczych).
String.prototype.splice = function(startIndex,length,insertString){ return this.substring(0,startIndex) + insertString + this.substring(startIndex + length); };
Możesz go używać w ten sposób:
var creditCardNumber = "5500000000000004"; var cardSuffix = creditCardNumber.splice(0,12,'****'); console.log(cardSuffix); // output: ****0004
Zobacz wyniki testu: https://jsfiddle.net/0quz9q9m/5/
źródło
, otherwise the third argument is not optional. This implementation also doesn't take care of
startIndex <0` w przeciwieństwie do innych sugestii. Świetny przykład użyciaWydaje się, że jest wiele nieporozumień, które zostały rozwiązane tylko w komentarzach elclanrs i raina77ow, więc pozwólcie, że opublikuję wyjaśniającą odpowiedź.
Wyjaśnienie
Z "
string.splice
” można by się tego spodziewać, podobnie jak w przypadku tablic:Problem w tym, że wymaganie 3d nie może zostać spełnione, ponieważ ciągi znaków są niezmienne (powiązane: 1 , 2 ), najbardziej dedykowany komentarz znalazłem tutaj :
Tak więc, biorąc to pod uwagę, można oczekiwać, że „
string.splice
” tylko:co jest tym, co
substr
robi; lub alternatywnieco jest tematem następnej sekcji.
Rozwiązania
Jeśli zależy Ci na optymalizacji, prawdopodobnie powinieneś skorzystać z implementacji Mike'a:
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); }
Traktowanie wskaźnika poza granicami może się jednak różnić. W zależności od potrzeb możesz chcieć:
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; }
lub nawet
index = index % this.length; if (index < 0) index = this.length + index;
Jeśli nie zależy Ci na wydajności, możesz dostosować sugestię Kumara, która jest prostsza:
String.prototype.splice = function(index, count, add) { var chars = this.split(''); chars.splice(index, count, add); return chars.join(''); }
Występ
Różnica w wykonaniu drastycznie rośnie wraz z długością struny. jsperf pokazuje , że dla łańcuchów o długości 10 to drugie rozwiązanie (dzielenie i łączenie) jest dwukrotnie wolniejsze niż poprzednie rozwiązanie (z użyciem plasterka), dla 100-literowych łańcuchów to x5, a dla 1000-literowych to x50, w Ops / s to:
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
zwróć uwagę, że zmieniłem argumenty 1. i 2. przy przechodzeniu z 10 liter na 100 liter (nadal jestem zaskoczony, że test na 100 liter działa szybciej niż na 10 liter).
źródło
Po prostu użyj substr jako string
dawny.
var str = "Hello world!"; var res = str.substr(1, str.length);
Wynik = świat ello!
źródło
Tak więc, niezależnie od dodania metody łączenia do prototypu String, nie można działać przezroczysto zgodnie ze specyfikacją ...
Zróbmy to komuś przedłużyć:
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; }
źródło
Metoda odpowiedzi Louisa , jako
String
funkcja prototypowa:String.prototype.splice = function(index, count, add) { if (index < 0) { index = this.length + index; if (index < 0) { index = 0; } } return this.slice(0, index) + (add || "") + this.slice(index + count); }
Przykład:
> "Held!".splice(3,0,"lo Worl") < "Hello World!"
źródło
Metoda spliceSlice Louisa zawodzi, gdy wartość dodania wynosi 0 lub inne fałszywe wartości, oto poprawka:
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); }
źródło
Rozwiązałem swój problem za pomocą tego kodu, jest to swego rodzaju zamiennik brakującego splotu.
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 }
Musiałem usunąć znak przed / po pewnym słowie, po uzyskaniu pozycji ciąg jest dzielony na dwie, a następnie ponownie składany przez elastyczne usuwanie znaków za pomocą przesunięcia wzdłuż
pos
źródło