754

I have a string, let's say Hello world and I need to replace the char at index 3. How can I replace a char by specifying a index?

var str = "hello world";

I need something like

str.replaceAt(0,"h");
informatik01
  • 16,038
  • 10
  • 74
  • 104
Santhosh
  • 19,616
  • 22
  • 63
  • 74
  • 248
    What's weird is that `str[0] = 'x'` doesn't seem to throw any errors, yet doesn't have the desired effect! – Michael Nov 15 '13 at 19:43
  • 9
    @Michael with that you would get the index at 0, set it to 'x', that statement at itself would return the new value; 'x'. but all of it doesnt change the origional, so its perfectly valid, just not what you expected. its not a reference – Paul Scheltema Nov 21 '13 at 14:46
  • 17
    @Michael it does if `"use strict"` is activated: `Uncaught TypeError: Cannot assign to read only property '0' of string 'hello world'` (at least in webkit browsers) – Jan Turoň Oct 27 '16 at 20:15
  • 9
    Javascript strings are immutable, they cannot be modified "in place" so you cannot modify a single character. in fact every occurence of the same string is ONE object. – Martijn Scheffer May 07 '19 at 20:33

30 Answers30

818

In JavaScript, strings are immutable, which means the best you can do is to create a new string with the changed content and assign the variable to point to it.

You'll need to define the replaceAt() function yourself:

String.prototype.replaceAt = function(index, replacement) {
    return this.substring(0, index) + replacement + this.substring(index + replacement.length);
}

And use it like this:

var hello = "Hello World";
alert(hello.replaceAt(2, "!!")); // He!!o World
Cem Kalyoncu
  • 14,120
  • 4
  • 40
  • 62
  • 175
    Note that it's generally not a good idea to extend base JavaScript classes. Use a plain utility function instead. – Ates Goral Sep 16 '09 at 05:40
  • 99
    I must ask why? Prototype support is there for this purpose. – Cem Kalyoncu Sep 16 '09 at 06:58
  • 41
    @CemKalyoncu: It *can* make code play bad with other libraries. But I haven't ever been bitten by that myself. – alex Jul 21 '11 at 04:53
  • 8
    @alex: you are right about that, you really need to check if that function exists before doing it. But still even if it does, it should do exactly the same operation. – Cem Kalyoncu Jul 21 '11 at 10:11
  • 105
    I disagree, even if you detect whether the function exists a later library may still use/create a similar function -- 2 bad ideas making a worse one. In general, just never play around with other peoples code (include the core system). Create a new function. – martyman Jun 05 '12 at 01:05
  • 2
    It's good to note that if you pass a number as the character parameter, it will insert at the index instead of replacing the character at the index with it. – Jeff LaFay Jun 14 '13 at 14:16
  • 5
    `substring` tends to be faster than `substr` or `slice`, if you care about micro-optimizing. – Azmisov Aug 07 '13 at 20:24
  • 2
    @CemKalyoncu Adding any method to the native object or even to the prototype makes it "listable" when using `for in` statement on this object instances. That's why I agree @AtesGoral – jmpp May 14 '14 at 18:33
  • @jmpp You could get around that by using [`Object.defineProperty`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/defineProperty) instead of direct assignment, I guess. – Utkan Gezer Sep 04 '14 at 17:53
  • 2
    This argument continues in 2015- to extend or not extend. However I would point out that either way there is the potential for naming collisions. It's just a question of where you prefer to chance it- at the prototype level or in the global window scope. – user2782001 Mar 06 '15 at 16:44
  • @CemKalyoncu So your proposing we create global functions that do what we can do by extending the prototype but if we all did that it is just as likely that we would run into conflicts with our global functions now overwriting each other. So either way conflicts are equally likely but one way is polluting the global namespace and requires an extra parameter (the string). They gave us prototypes for a reason... – Dustin Poissant Oct 10 '15 at 21:30
  • @user2782001 Using ES 6 modules with a transpiler (or any other kind of import system together with a build script) completely eliminates the scope pollution problem. If that's too fancy for you, a poor man's solution is to just create a single global object that you put all of your functions onto. – Mark Amery Nov 29 '15 at 15:31
  • TC39 has already been bitten by MooTools extending built-in prototypes. – gcampbell Aug 08 '16 at 18:42
  • More on why this is not a good idea: https://github.com/tc39/proposal-flatMap/pull/56 – Jorjon May 17 '18 at 02:39
  • 2
    Please do not edit the answer to reflect your opinion. John has suggested using a different naming system to avoid name collision. But I stand behind my decision. If you need to do this, you are probably not using any other library that has similar functionality. Even if it exists, nothing would change because the function does what it says it does. If you are implementing this function with the same and with different functionality, you shouldn't call yourself a programmer and distribute your library. – Cem Kalyoncu May 18 '18 at 17:45
  • As a reference, [don't modify objects you don't own](https://stackoverflow.com/q/14034180/1218980). – Emile Bergeron Mar 04 '19 at 14:56
  • Be aware that if the string has combining marks (for example: let str = 'e\u0301'), the result is maybe not the one you wants. Manipulating multibytes string is hard. – Synn Jan 10 '20 at 09:58
  • 1
    You can try this also, works fine with replace with empty string. String.prototype.replaceAt = function(index, replacement) { return this.slice(0, index) + replacement + this.slice(index + 1); } – Amar Nov 04 '20 at 12:58
  • .replaceAt should function in Javascript. It would be very useful and convenient. – FireTiger Jan 13 '21 at 21:28
  • `substr` has been deprecated can you please update the answer with `substring` or `slice` ? thanks – jave.web Mar 26 '22 at 07:54
  • @jave.web Sure, only thing is to change is the function name, it will still work the same way. – Cem Kalyoncu Mar 26 '22 at 17:26
  • @CemKalyoncu, I know, but just to prevent many unecessary deprecations in future :) Your answer is of great impact ;) – jave.web Mar 29 '22 at 09:49
  • @Jave.web you can always update it yourself. No need to ask the original author for permission, though a comment as to why the edit was added is always polite. If he is unhappy with the edit he can reject the edit, or roll it back. Most people are sane enough to appreciate the help, Though there are the concessional few, who can, at times, make make humanity look like a hopeless lot. – JΛYDΞV Jun 30 '22 at 03:34
159

There is no replaceAt function in JavaScript. You can use the following code to replace any character in any string at specified position:

function rep() {
    var str = 'Hello World';
    str = setCharAt(str,4,'a');
    alert(str);
}

function setCharAt(str,index,chr) {
    if(index > str.length-1) return str;
    return str.substring(0,index) + chr + str.substring(index+1);
}
<button onclick="rep();">click</button>
rahul
  • 184,426
  • 49
  • 232
  • 263
  • I prefere this solution because you can replace a single character with it. The solution that has the most upvotes doesn't work if you want to replace only one character. It only works when replacing two characters! Also, substr should be replaced with substring as mentioned in many other comments. – gignu Jan 14 '20 at 11:31
  • 1
    In my tests this method was quickest by far... and even faster if you don't need to verify that [index] isn't bigger than the string length. Modified: `function setCharAt(str,idx,newChr){ return str.substring(0,idx)+newChr+str.substring(idx+1);}` – ashleedawg Sep 10 '20 at 07:09
  • 1
    @ScottTesler - This answer uses `substring`, not `substr`... and where in your link does it say that either function is "legacy" or should be avoided? ...[`substring`](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/String/substring) and [`substr`](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/String/substr) serve [different purposes](https://stackoverflow.com/q/3745515/8112776). – ashleedawg Sep 10 '20 at 07:13
  • @ashleedawg It looks like it's no longer deprecated. – Scott Tesler Sep 11 '20 at 20:46
120

You can't. Take the characters before and after the position and concat into a new string:

var s = "Hello world";
var index = 3;
s = s.substring(0, index) + 'x' + s.substring(index + 1);
zendka
  • 1,074
  • 12
  • 11
Guffa
  • 687,336
  • 108
  • 737
  • 1,005
  • Actually, yes, you can, but it would be an overkill. You could set up a regular expression to skip the first index - 1 characters and match the character at the index. You can use String.replace with that regular expression to do a direct, in-place replacement. But it's an overkill. So, in practice you can't. But in theory, you can. – Ates Goral Sep 16 '09 at 05:42
  • 15
    @Ates: The replace function doesn't do an in-place replacement, it creates a new string and returns it. – Guffa Sep 16 '09 at 05:55
  • 4
    [MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/substr) suggests to use `String.prototype.substring` over `String.prototype.substr`. – Michał Terczyński Feb 10 '19 at 11:55
74
str = str.split('');
str[3] = 'h';
str = str.join('');
colllin
  • 9,442
  • 9
  • 49
  • 65
  • 9
    Clear and simple, but currently won't work with emoji (such as ) when using `split` and `join` – Green Jun 26 '16 at 10:15
  • 4
    With es6 I think that Array.from(str) might be a better option now, but I came here with that knowledge and learned something just as concise from you so thank you! – David Kamer Jun 23 '18 at 03:23
  • 1
    @DavidKamer I'm late to the party, but it seems `Array.from` is significantly slower than `str.split`. https://blog.shovonhasan.com/never-use-array-from-to-convert-strings-to-arrays/ – Charles Oct 08 '21 at 12:05
  • @Green if your string contains emojis it's probably a user input, hence I don't think there are obvious reasons to change a character in the string using this method, if you want to change a part in an input transformation scenario you should use `replace` method with regexp instead. – vdegenne Mar 24 '22 at 10:47
  • Is there a way to replace multiple areas? Something like - `str[3, 5] = h`? –  Apr 07 '22 at 01:14
  • 1
    @KadenSkinner It's an array, so you could `str.splice(3, h.length, ...h.split(''))` or `str.splice.apply(str, [3, h.length].concat(h.split('')))` but this seems crazy compared to `str.substring(0,3) + h + str.substring(5)`. – colllin Apr 07 '22 at 18:27
  • @colllin Thanks! I appreciate it. I couldn't really understand what you meant until I looked at the documentation. XD Thanks for the hint! –  Apr 08 '22 at 01:35
  • Note that `'124'.length` is **5**, not 4. So, if you're doing things in an automated fashion, depending on what exactly you're trying to do, emojis might not be a problem anyway, especially if looping with a `for (let i = 0 ...` pattern. – aggregate1166877 May 04 '23 at 11:41
36

There are lot of answers here, and all of them are based on two methods:

  • METHOD1: split the string using two substrings and stuff the character between them
  • METHOD2: convert the string to character array, replace one array member and join it

Personally, I would use these two methods in different cases. Let me explain.

@FabioPhms: Your method was the one I initially used and I was afraid that it is bad on string with lots of characters. However, question is what's a lot of characters? I tested it on 10 "lorem ipsum" paragraphs and it took a few milliseconds. Then I tested it on 10 times larger string - there was really no big difference. Hm.

@vsync, @Cory Mawhorter: Your comments are unambiguous; however, again, what is a large string? I agree that for 32...100kb performance should better and one should use substring-variant for this one operation of character replacement.

But what will happen if I have to make quite a few replacements?

I needed to perform my own tests to prove what is faster in that case. Let's say we have an algorithm that will manipulate a relatively short string that consists of 1000 characters. We expect that in average each character in that string will be replaced ~100 times. So, the code to test something like this is:

var str = "... {A LARGE STRING HERE} ...";

for(var i=0; i<100000; i++)
{
  var n = '' + Math.floor(Math.random() * 10);
  var p = Math.floor(Math.random() * 1000);
  // replace character *n* on position *p*
}

I created a fiddle for this, and it's here. There are two tests, TEST1 (substring) and TEST2 (array conversion).

Results:

  • TEST1: 195ms
  • TEST2: 6ms

It seems that array conversion beats substring by 2 orders of magnitude! So - what the hell happened here???

What actually happens is that all operations in TEST2 are done on array itself, using assignment expression like strarr2[p] = n. Assignment is really fast compared to substring on a large string, and its clear that it's going to win.

So, it's all about choosing the right tool for the job. Again.

OzrenTkalcecKrznaric
  • 5,535
  • 4
  • 34
  • 57
  • 7
    Moved your test to jsperf, with vastly different results: http://jsperf.com/string-replace-character. It's all about choosing the right tool for the job ;) – colllin Oct 30 '14 at 03:11
  • 1
    @colllin: I absolutely agree. So I almost literally cloned the tests from jsfiddle to jsperf. However, aside from using the right tool, you have to do it in the right way. Pay attention to the problem, we're talking about what will happen if we have to make quite a few replacements in an algorithm. The concrete example includes 10000 replacements. This means *one test* should include 10000 replacements. So, using jsperf, I got quite consistent results, see: http://jsperf.com/replace-a-character-at-a-particular-index-in-javascript. – OzrenTkalcecKrznaric Oct 30 '14 at 09:22
  • 1
    this is why i don't like javascript. such frequent, intuitive, obvious use cases aren't provisioned for. You'd think it would occur to the writers of javascript that people may want to substitute characters within strings, and that they'd decide to put in convenience methods into the language. – ahnbizcad Mar 26 '15 at 04:43
  • 1
    @colllin did something different to OzrenTkalcecKrznaric. OzrenTkalcecKrznaric made the assumption that the string is static and and the split can be optimized before the runs. Which is not necessarily true. if you have to split at every run then the substring approach is about twice-4x faster on small strings, and only faster the bigger the string gets. In my opinion this makes the substring the better implementation for most use cases, barring large numbers of changes on a large static string. – WiR3D Mar 02 '16 at 15:33
  • @WiR3D: Actually there is no assumption. I've shown how a case behaves for two algorithms. And I can agree that case isn't something you would stumble upon in most situations. This just goes to show that if you say something is generally faster, better, more acceptable or whatever, you will fail. Sometimes substring is better, sometimes not. Again - choose the right tool for the job ;) – OzrenTkalcecKrznaric Mar 22 '16 at 08:33
  • 4
    The problem is that on test2 the split and join are outside the for loop, where you compare single char replacement with a multiple one (unfair), the first method is faster for single replacements and the second one is better for chained replacements one after another – Theofilos Mouratidis Jul 22 '16 at 11:40
  • Exactly. As I said, it's all about choosing the right tool for the job. – OzrenTkalcecKrznaric Jul 22 '16 at 11:54
  • 1
    This is old, but should be... i saw the same as @ΘεόφιλοςΜουρατίδης did, but checked myself (made a version that convert to array for each string... and still Test#2 is better (though not by much) (see http://jsfiddle.net/TomerW/rsjop8yw/21/) – Tomer W Sep 29 '20 at 15:25
  • @TomerW in your fiddle, you happened to test `replaceAt1` against itself.. when you change to test `replaceAt1` vs. `replaceAt2` then you see that `replaceAt1` (aka. TEST#1) is an order of magnitude faster: http://jsfiddle.net/1rxwmthc/ – Magne Apr 29 '22 at 07:42
  • This is an unfair test, since METHOD1 and METHOD2 are tested on different grounds as Theofilos said. Ofc METHOD2 `convert the string to character array, replace one array member, and join it` is faster, if `convert the string to character array` and `and join it` is done outside of the test... It's testing the internals of METHOD2 against the whole of METHOD1. The fairer test would be: http://jsfiddle.net/1rxwmthc/ In general: METHOD1 will iterate the whole string once (the head plus the tail), whereas METHOD2 will iterate it fully twice (once for the split, and once for the join). – Magne Apr 29 '22 at 07:51
35

Work with vectors is usually most effective to contact String.

I suggest the following function:

String.prototype.replaceAt=function(index, char) {
    var a = this.split("");
    a[index] = char;
    return a.join("");
}

Run this snippet:

String.prototype.replaceAt=function(index, char) {
    var a = this.split("");
    a[index] = char;
    return a.join("");
}

var str = "hello world";
str = str.replaceAt(3, "#");

document.write(str);
Fabio Phms
  • 9,890
  • 1
  • 15
  • 9
  • 11
    this is bad for large strings, no need to create an Array with crazy amount of cells if you can just use substr to cut it... – vsync Oct 24 '11 at 08:30
  • 1
    Useful if you need to change a lot of characters, and it is simple. – Sheepy Aug 22 '12 at 02:02
  • 7
    I created a test on jsperf: http://jsperf.com/replace-character-by-index -- Substr is way faster, and consistent from 32bytes up to 100kb. I upvoted this and as much as it hurts me to say, even though this feels nicer, substr is the better choice for strings of any size. – Cory Mawhorter May 09 '13 at 03:37
  • This is quite unoptimal. – Radko Dinev Aug 25 '14 at 07:09
  • This is a good quick solution if you know you are going to use small strings. If you are okay with extending the prototypes, then you could achieve similar behavior in 2 lines: `Array.prototype.replace = function(index, val) { this[index] = val; return this; };` `'word'.split('').replace(1, '0').join(''); // returns 'w0rd'` – Michael Plautz Mar 20 '18 at 15:04
34

In Javascript strings are immutable so you have to do something like

var x = "Hello world"
x = x.substring(0, i) + 'h' + x.substring(i+1);

To replace the character in x at i with 'h'

colllin
  • 9,442
  • 9
  • 49
  • 65
DevDevDev
  • 5,107
  • 7
  • 55
  • 87
19

function dothis() {
  var x = document.getElementById("x").value;
  var index = document.getElementById("index").value;
  var text = document.getElementById("text").value;
  var length = document.getElementById("length").value;
  var arr = x.split("");
  arr.splice(index, length, text);
  var result = arr.join("");
  document.getElementById('output').innerHTML = result;
  console.log(result);
}
dothis();
<input id="x" type="text" value="White Dog" placeholder="Enter Text" />
<input id="index" type="number" min="0"value="6" style="width:50px" placeholder="index" />
<input id="length" type="number" min="0"value="1" style="width:50px" placeholder="length" />
<input id="text" type="text" value="F" placeholder="New character" />
<br>
<button id="submit" onclick="dothis()">Run</button>
<p id="output"></p>

This method is good for small length strings but may be slow for larger text.

var x = "White Dog";
var arr = x.split(""); // ["W", "h", "i", "t", "e", " ", "D", "o", "g"]
arr.splice(6, 1, 'F');

/* 
  Here 6 is starting index and 1 is no. of array elements to remove and 
  final argument 'F' is the new character to be inserted. 
*/
var result = arr.join(""); // "White Fog"
Vikramaditya
  • 5,444
  • 6
  • 34
  • 45
  • 1
    Up voted because I found the extra description to be useful and the implementation simple and powerful. Thank you! :-D – Seth Eden Jun 24 '20 at 21:55
  • [Array.from](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/from) might also be a good idea for string to array conversion – Valen Jul 25 '20 at 09:51
  • Yes `Array.from` can also be used here. but Array.from was added in ES2015 and has no support in older browsers. Also, i personally prefer `split` function because it gives more freedom to play with the string patterns. – Vikramaditya Jul 26 '20 at 17:42
  • 1
    If you want to replace just 1 character you can use `arr[6]='F';` instead of `.splice()`. – Jay Dadhania Feb 13 '21 at 19:14
  • What you have suggested was already suggested by @fabio-phms in the [answer above](https://stackoverflow.com/a/7382461/1439321). i was just looking through another point of view where we have flexibility to replace one or more characters. – Vikramaditya Feb 14 '21 at 21:00
18

One-liner using String.replace with callback (no emoji support):

// 0 - index to replace, 'f' - replacement string
'dog'.replace(/./g, (c, i) => i == 0? 'f': c)
// "fog"

Explained:

//String.replace will call the callback on each pattern match
//in this case - each character
'dog'.replace(/./g, function (character, index) {
   if (index == 0) //we want to replace the first character
     return 'f'
   return character //leaving other characters the same
})
Afanasii Kurakin
  • 3,330
  • 2
  • 24
  • 26
  • 1
    beautifully simplistic - great option that doesn't force extending the prototype or creating new functions. Thank you! – Brian Powell May 11 '21 at 17:13
11

Generalizing Afanasii Kurakin's answer, we have:

function replaceAt(str, index, ch) {
    return str.replace(/./g, (c, i) => i == index ? ch : c);
}

let str = 'Hello World';
str = replaceAt(str, 1, 'u');
console.log(str); // Hullo World

Let's expand and explain both the regular expression and the replacer function:

function replaceAt(str, index, newChar) {
    function replacer(origChar, strIndex) {
        if (strIndex === index)
            return newChar;
        else
            return origChar;
    }
    return str.replace(/./g, replacer);
}

let str = 'Hello World';
str = replaceAt(str, 1, 'u');
console.log(str); // Hullo World

The regular expression . matches exactly one character. The g makes it match every character in a for loop. The replacer function is called given both the original character and the index of where that character is in the string. We make a simple if statement to determine if we're going to return either origChar or newChar.

Stephen Quan
  • 21,481
  • 4
  • 88
  • 75
6

var str = "hello world";
console.log(str);
var arr = [...str];
arr[0] = "H";
str = arr.join("");
console.log(str);
Avi Cohen
  • 3,102
  • 2
  • 25
  • 26
  • This is as poorly explained as [this conceptually identical answer from 2018](https://stackoverflow.com/a/53368829/1269037). What does this answer add? – Dan Dascalescu Sep 27 '22 at 07:03
  • @DanDascalescu sometimes the presentation makes the difference, not only the content. it got 5 upvotes after all. – Avi Cohen Sep 27 '22 at 14:54
5

This works similar to Array.splice:

String.prototype.splice = function (i, j, str) {
    return this.substr(0, i) + str + this.substr(j, this.length);
};
Aram Kocharyan
  • 20,165
  • 11
  • 81
  • 96
5

You could try

var strArr = str.split("");

strArr[0] = 'h';

str = strArr.join("");
Mehulkumar
  • 836
  • 2
  • 10
  • 23
5

this is easily achievable with RegExp!

const str = 'Hello RegEx!';
const index = 11;
const replaceWith = 'p';

//'Hello RegEx!'.replace(/^(.{11})(.)/, `$1p`);
str.replace(new RegExp(`^(.{${ index }})(.)`), `$1${ replaceWith }`);

//< "Hello RegExp"
Madmadi
  • 2,064
  • 1
  • 14
  • 17
  • 1
    As far as contemporary JavaScript goes, in 2022, this is by far the best answer. – JΛYDΞV Jun 30 '22 at 04:24
  • 1
    For the record, lookbehind can be used to avoid capturing groups. Haven't checked performance implications of this approach (which could be a big concern), but it leads to overall simplification: `str.replace(new RegExp(\`(?<=^.{${index}}).\`), replaceWith)` – Sergii Shymko Dec 10 '22 at 04:09
5

You could try

var strArr = str.split("");

strArr[0] = 'h';

str = strArr.join("");

Check out this function for printing steps

steps(3)
//       '#  '
//       '## '
//       '###'

function steps(n, i = 0, arr = Array(n).fill(' ').join('')) {
  if (i === n) {
    return;
  }

  str = arr.split('');
  str[i] = '#';
  str = str.join('');
  console.log(str);

  steps(n, (i = i + 1), str);
}

Magne
  • 16,401
  • 10
  • 68
  • 88
Ridwan Ajibola
  • 873
  • 11
  • 16
5

Using the spread syntax, you may convert the string to an array, assign the character at the given position, and convert back to a string:

const str = "hello world";

function replaceAt(s, i, c) {
  const arr = [...s];  // Convert string to array
  arr[i] = c;          // Set char c at pos i
  return arr.join(''); // Back to string
}

// prints "hallo world"
console.log(replaceAt(str, 1, 'a'));
Gyum Fox
  • 3,287
  • 2
  • 41
  • 71
  • I would be careful in putting this into a function like this. Because inevitably someone will run the function inside a loop. Which in this case will be terribly suboptimal compared to if they had to simply write the "convert to array" and "join" themselves, when they needed it. Then they'd naturally put it outside the loop. – Magne Apr 29 '22 at 07:59
4

@CemKalyoncu: Thanks for the great answer!

I also adapted it slightly to make it more like the Array.splice method (and took @Ates' note into consideration):

spliceString=function(string, index, numToDelete, char) {
      return string.substr(0, index) + char + string.substr(index+numToDelete);
   }

var myString="hello world!";
spliceString(myString,myString.lastIndexOf('l'),2,'mhole'); // "hello wormhole!"
Scrimothy
  • 2,536
  • 14
  • 23
  • Not sure why this was voted down. It's a legit answer. It works as indicated. And it's consistent with `Array.splice` type functionality. – Scrimothy May 18 '15 at 14:40
3

You can extend the string type to include the inset method:

String.prototype.append = function (index,value) {
  return this.slice(0,index) + value + this.slice(index);
};

var s = "New string";
alert(s.append(4,"complete "));

Then you can call the function:

mbadeveloper
  • 1,272
  • 9
  • 16
3

If you want to replace characters in string, you should create mutable strings. These are essentially character arrays. You could create a factory:

  function MutableString(str) {
    var result = str.split("");
    result.toString = function() {
      return this.join("");
    }
    return result;
  }

Then you can access the characters and the whole array converts to string when used as string:

  var x = MutableString("Hello");
  x[0] = "B"; // yes, we can alter the character
  x.push("!"); // good performance: no new string is created
  var y = "Hi, "+x; // converted to string: "Hi, Bello!"
Jan Turoň
  • 31,451
  • 23
  • 125
  • 169
2

You can concatenate using sub-string function at first select text before targeted index and after targeted index then concatenate with your potential char or string. This one is better

const myString = "Hello world";
const index = 3;
const stringBeforeIndex = myString.substring(0, index);
const stringAfterIndex = myString.substring(index + 1);
const replaceChar = "X";
myString = stringBeforeIndex + replaceChar + stringAfterIndex;
console.log("New string - ", myString)

or

const myString = "Hello world";
let index = 3;
myString =  myString.substring(0, index) + "X" + myString.substring(index + 1);
MD SHAYON
  • 7,001
  • 45
  • 38
2

My safe approach with negative indexes:

/**
 * @param {string} str
 * @param {number} index
 * @param {string} replacement
 * @returns {string}
 */
function replaceAt(str, index, replacement) {
  if (index < 0) index = str.length + index;
  if (index < 0 || index >= str.length)
    throw new Error(`Index (${index}) out of bounds "${str}"`);
  return str.substring(0, index) + replacement + str.substring(index + 1);
}

Use it like this:

replaceAt('my string', -1, 'G') // 'my strinG'
replaceAt('my string', 2, 'yy') // 'myyystring'
replaceAt('my string', 22, 'yy') // Uncaught Error: Index (22) out of bounds "my string"
Andreas Violaris
  • 2,465
  • 5
  • 13
  • 26
Alexandre Daubricourt
  • 3,323
  • 1
  • 34
  • 33
1

I did a function that does something similar to what you ask, it checks if a character in string is in an array of not allowed characters if it is it replaces it with ''

    var validate = function(value){
        var notAllowed = [";","_",">","<","'","%","$","&","/","|",":","=","*"];
        for(var i=0; i<value.length; i++){
            if(notAllowed.indexOf(value.charAt(i)) > -1){
               value = value.replace(value.charAt(i), "");
               value = validate(value);
            }
       }
      return value;
   }
revelt
  • 2,312
  • 1
  • 25
  • 37
mirzak
  • 1,043
  • 4
  • 15
  • 30
1

Here is a version I came up with if you want to style words or individual characters at their index in react/javascript.

replaceAt( yourArrayOfIndexes, yourString/orArrayOfStrings ) 

Working example: https://codesandbox.io/s/ov7zxp9mjq

function replaceAt(indexArray, [...string]) {
    const replaceValue = i => string[i] = <b>{string[i]}</b>;
    indexArray.forEach(replaceValue);
    return string;
}

And here is another alternate method

function replaceAt(indexArray, [...string]) {
    const startTag = '<b>';
    const endTag = '</b>';
    const tagLetter = i => string.splice(i, 1, startTag + string[i] + endTag);
    indexArray.forEach(tagLetter);
    return string.join('');
}

And another...

function replaceAt(indexArray, [...string]) {
    for (let i = 0; i < indexArray.length; i++) {
        string = Object.assign(string, {
          [indexArray[i]]: <b>{string[indexArray[i]]}</b>
        });
    }
    return string;
}
Matt Wright
  • 102
  • 1
  • 4
1

Here is my solution using the ternary and map operator. More readable, maintainable end easier to understand if you ask me.

It is more into es6 and best practices.

function replaceAt() {
  const replaceAt = document.getElementById('replaceAt').value;

  const str = 'ThisIsATestStringToReplaceCharAtSomePosition';
  const newStr = Array.from(str).map((character, charIndex) => charIndex === (replaceAt - 1) ? '' : character).join('');

  console.log(`New string: ${newStr}`);
}
<input type="number" id="replaceAt" min="1" max="44" oninput="replaceAt()"/>
karlo1zg
  • 180
  • 3
  • 17
0

Lets say you want to replace Kth index (0-based index) with 'Z'. You could use Regex to do this.

var re = var re = new RegExp("((.){" + K + "})((.){1})")
str.replace(re, "$1A$`");
ksp
  • 132
  • 1
  • 5
  • Any idea why is this tagged not useful? – ksp Mar 17 '17 at 21:05
  • 1
    I haven't checked if this regex works, but maybe it's downvoted because it's probably a lot faster to create a new string, than compiling a state machine (regular expression), which is very expensive. – Chris Vilches Apr 08 '17 at 15:29
  • This answer also has errors, it has a syntax error where `var re = var re` and it has a semantic error, where it uses without `$\`` any need – flen Jul 27 '23 at 06:02
0

You can use the following function to replace Character or String at a particular position of a String. To replace all the following match cases use String.prototype.replaceAllMatches() function.

String.prototype.replaceMatch = function(matchkey, replaceStr, matchIndex) {
    var retStr = this, repeatedIndex = 0;
    for (var x = 0; (matchkey != null) && (retStr.indexOf(matchkey) > -1); x++) {
        if (repeatedIndex == 0 && x == 0) {
            repeatedIndex = retStr.indexOf(matchkey);
        } else { // matchIndex > 0
            repeatedIndex = retStr.indexOf(matchkey, repeatedIndex + 1);
        }
        if (x == matchIndex) {
            retStr = retStr.substring(0, repeatedIndex) + replaceStr + retStr.substring(repeatedIndex + (matchkey.length));
            matchkey = null; // To break the loop.
        }
    }
    return retStr;
};

Test:

var str = "yash yas $dfdas.**";

console.log('Index Matched replace : ', str.replaceMatch('as', '*', 2) );
console.log('Index Matched replace : ', str.replaceMatch('y', '~', 1) );

Output:

Index Matched replace :  yash yas $dfd*.**
Index Matched replace :  yash ~as $dfdas.**
Yash
  • 9,250
  • 2
  • 69
  • 74
0

I se this to make a string proper case, that is, the first letter is Upper Case and all the rest are lower case:

function toProperCase(someString){
    
    return someString.charAt(0).toUpperCase().concat(someString.toLowerCase().substring(1,someString.length));
    
};

This first thing done is to ensure ALL the string is lower case - someString.toLowerCase()

then it converts the very first character to upper case -someString.charAt(0).toUpperCase()

then it takes a substring of the remaining string less the first character -someString.toLowerCase().substring(1,someString.length))

then it concatenates the two and returns the new string -someString.charAt(0).toUpperCase().concat(someString.toLowerCase().substring(1,someString.length))

New parameters could be added for the replacement character index and the replacement character, then two substrings formed and the indexed character replaced then concatenated in much the same way.

desertnaut
  • 57,590
  • 26
  • 140
  • 166
  • To achieve 'proper case', would it be less complicated to make the whole string lower case, then capitalize the first character? You wouldn't have to deal with a substring then. – Jeter-work Apr 11 '23 at 14:38
-1

The solution does not work for negative index so I add a patch to it.

String.prototype.replaceAt=function(index, character) {
    if(index>-1) return this.substr(0, index) + character + this.substr(index+character.length);
    else return this.substr(0, this.length+index) + character + this.substr(index+character.length);
    
}
desertnaut
  • 57,590
  • 26
  • 140
  • 166
cesar moro
  • 168
  • 8
-3
"hello world".replace(/(.{3})./, "$1h")
// 'helho world'
pguardiario
  • 53,827
  • 19
  • 119
  • 159
-4

The methods on here are complicated. I would do it this way:

var myString = "this is my string";
myString = myString.replace(myString.charAt(number goes here), "insert replacement here");

This is as simple as it gets.

mikey
  • 65
  • 1
  • 3