Bagaimana Anda membalikkan string di JavaScript?


435

Bagaimana Anda membalikkan string di tempat (atau di tempat) di JavaScript ketika dilewatkan ke fungsi dengan pernyataan pengembalian, tanpa menggunakan fungsi bawaan ( .reverse(), .charAt()dll.)?


jadi, Anda tidak diizinkan menggunakan .charAt () untuk mendapatkan karakter string?
Irwin

155
Kamu tidak bisa String JavaScript tidak dapat diubah, artinya memori yang dialokasikan untuk masing-masing tidak dapat ditulis, membuat pembalikan "in place" yang benar menjadi tidak mungkin.
Crescent Fresh

2
Re: komentar crescentfresh lihat stackoverflow.com/questions/51185/…
baudtack

1
@crescentfresh Anda harus memposting itu sebagai jawaban baru.
baudtack

Jawaban:


737

Selama Anda berurusan dengan karakter ASCII sederhana, dan Anda senang menggunakan fungsi bawaan, ini akan berfungsi:

function reverse(s){
    return s.split("").reverse().join("");
}

Jika Anda membutuhkan solusi yang mendukung UTF-16 atau karakter multi-byte lainnya, perlu diketahui bahwa fungsi ini akan memberikan string unicode yang tidak valid, atau string yang valid yang terlihat lucu. Anda mungkin ingin mempertimbangkan jawaban ini sebagai gantinya .

[... s] menyadari Unicode, hasil edit kecil memberikan: -

function reverse(s){
    return [...s].reverse().join("");
}

44
Ini rusak untuk string UTF-16 yang berisi pasangan pengganti, yaitu karakter di luar bidang multibahasa dasar. Ini juga akan memberikan hasil yang lucu untuk string yang berisi kombinasi chars, misalnya diaeresis mungkin muncul pada karakter berikut. Masalah pertama akan menyebabkan string unicode yang tidak valid, yang kedua ke string yang valid yang terlihat lucu.
Martin Probst

2
@Richeve Bebedor "Semua tanpa menggunakan fungsi bawaan? .Reverse ()" Ini tidak akan menjadi solusi yang diterima karena tidak sesuai dengan batas-batas pertanyaan, meskipun merupakan solusi yang layak untuk membalikkan string di JS.
David Starkey

1
@ Davidvidarkarkey: Ya, melihat kembali ini hampir empat tahun kemudian, sulit untuk melihat bagaimana saya benar-benar kehilangan titik pertanyaan. Sepertinya saya seharusnya hanya menunggu dua menit dan meningkatkan komentar crescentfresh pada posting asli!
belacqua

14
@MartinProbst Jawaban saya memberikan solusi sadar Unicode untuk masalah yang berhubungan dengan pasangan pengganti dan menggabungkan tanda dengan benar: stackoverflow.com/a/16776380/96656
Mathias Bynens

1
Untuk UTF-16 return [...s].reverse().join("");dapat bekerja.
user4642212

411

Teknik berikut (atau serupa) biasanya digunakan untuk membalikkan string dalam JavaScript:

// Don’t use this!
var naiveReverse = function(string) {
    return string.split('').reverse().join('');
}

Faktanya, semua jawaban yang diposting sejauh ini adalah variasi dari pola ini. Namun, ada beberapa masalah dengan solusi ini. Sebagai contoh:

naiveReverse('foo 𝌆 bar');
// → 'rab �� oof'
// Where did the `𝌆` symbol go? Whoops!

Jika Anda bertanya-tanya mengapa ini terjadi, baca tentang pengodean karakter internal JavaScript . (TL; DR: 𝌆adalah simbol astral, dan JavaScript memaparkannya sebagai dua unit kode yang terpisah.)

Tapi ada lagi:

// To see which symbols are being used here, check:
// http://mothereff.in/js-escapes#1ma%C3%B1ana%20man%CC%83ana
naiveReverse('mañana mañana');
// → 'anãnam anañam'
// Wait, so now the tilde is applied to the `a` instead of the `n`? WAT.

String yang baik untuk menguji implementasi string terbalik adalah sebagai berikut :

'foo 𝌆 bar mañana mañana'

Mengapa? Karena itu mengandung simbol astral ( 𝌆) (yang diwakili oleh pasangan pengganti dalam JavaScript ) dan tanda menggabungkan ( yang terakhirmañana sebenarnya terdiri dari dua simbol: U + 006E LATIN KECIL SURAT N dan U + 0303 GABUNG GABUNG).

Urutan di mana pasangan pengganti muncul tidak dapat dibalik, selain itu simbol astral tidak akan muncul lagi dalam string 'terbalik'. Itu sebabnya Anda melihat ��tanda - tanda itu di keluaran untuk contoh sebelumnya.

Menggabungkan tanda selalu diterapkan pada simbol sebelumnya, jadi Anda harus memperlakukan kedua simbol utama (U + 006E LATIN SMALL LETTER N) sebagai tanda penggabungan (U + 0303 COMBINING TILDE) secara keseluruhan. Membalikkan urutannya akan menyebabkan tanda gabungan dipasangkan dengan simbol lain dalam string. Itu sebabnya contoh output bukan ñ.

Semoga ini menjelaskan mengapa semua jawaban yang diposting sejauh ini salah .


Untuk menjawab pertanyaan awal Anda - bagaimana [dengan benar] membalikkan string dalam JavaScript -, saya telah menulis perpustakaan JavaScript kecil yang mampu membalikkan string yang sadar-Unicode. Itu tidak memiliki masalah yang baru saja saya sebutkan. Perpustakaan disebut Esrever ; kodenya ada di GitHub, dan berfungsi di hampir semua lingkungan JavaScript. Itu datang dengan utilitas shell / biner, sehingga Anda dapat dengan mudah membalik string dari terminal Anda jika Anda mau.

var input = 'foo 𝌆 bar mañana mañana';
esrever.reverse(input);
// → 'anañam anañam rab 𝌆 oof'

Sedangkan untuk bagian "di tempat", lihat jawaban lainnya.


65
Anda harus memasukkan bagian utama dari kode Esrever dalam jawaban Anda.
r0estir0bbe

1
@Meglio Dengan pendekatan khusus itu, ya.
Mathias Bynens

8
Masalahnya, tentu saja, adalah bahwa "membalikkan sebuah string" terdengar tidak ambigu, tetapi itu tidak dalam menghadapi masalah yang disebutkan di sini. Apakah membalik string mengembalikan string yang ketika dicetak akan menampilkan cluster grapheme dalam string dalam urutan terbalik? Di satu sisi, itu terdengar mungkin. Di sisi lain, mengapa Anda ingin melakukan itu? Definisi ini bergantung pada itu sedang dicetak, dan mencetak string terbalik jarang berguna. Sebagai bagian dari suatu algoritma, persyaratan Anda mungkin berbeda sama sekali.
Martijn

19
Meskipun ini sangat membantu dalam menjelaskan masalah, jawaban sebenarnya ada di kastil lain . Seperti @ r0estir0bbe mengatakan lebih dari setahun yang lalu, kode yang relevan harus ada dalam jawabannya, bukan hanya ditautkan.
TJ Crowder

4
"Semoga ini menjelaskan mengapa semua jawaban yang diposting sejauh ini salah" - Pernyataan ini terlalu kuat. Banyak kasus penggunaan tidak memerlukan dukungan UTF-16 (contoh sederhana; bekerja dengan URL dan komponen / parameter URL). Sebuah solusi bukanlah "salah" hanya karena ia tidak menangani skenario yang tidak diperlukan. Khususnya, jawaban terpilih secara eksplisit menyatakan bahwa itu hanya bekerja dengan karakter ASCII dan dengan demikian jelas tidak sedikit salah.
Agustus

92
String.prototype.reverse_string=function() {return this.split("").reverse().join("");}

atau

String.prototype.reverse_string = function() {
    var s = "";
    var i = this.length;
    while (i>0) {
        s += this.substring(i-1,i);
        i--;
    }
    return s;
}

Saya pasti setuju dengan prototipe String.
Jeff Meatball Yang

3
penggabungan string mahal. Lebih baik membangun array dan bergabung atau gunakan concat ().
Bjorn

2
# 1 adalah yang terbaik, # 2 bisa sangat lambat
adamJLev

9
Namun, tidak ada solusi yang berfungsi saat karakter majemuk Unicode hadir.
Eric Grange

2
@JuanMendes Saya meninggalkan komentar itu pada tahun 2009, banyak hal telah berubah dalam 4 tahun terakhir. : P
Bjorn

63

Analisis terperinci dan sepuluh cara berbeda untuk membalik string dan detail kinerja mereka.

http://eddmann.com/posts/ten-ways-to-reverse-a-string-in-javascript/

Kinerja implementasi ini:

Implementasi berkinerja terbaik per browser

  • Chrome 15 - Implemations 1 dan 6
  • Firefox 7 - Implementasi 6
  • IE 9 - Implementasi 4
  • Opera 12 - Implementasi 9

Berikut adalah implementasinya:

Implementasi 1:

function reverse(s) {
  var o = '';
  for (var i = s.length - 1; i >= 0; i--)
    o += s[i];
  return o;
}

Implementasi 2:

function reverse(s) {
  var o = [];
  for (var i = s.length - 1, j = 0; i >= 0; i--, j++)
    o[j] = s[i];
  return o.join('');
}

Implementasi 3:

function reverse(s) {
  var o = [];
  for (var i = 0, len = s.length; i <= len; i++)
    o.push(s.charAt(len - i));
  return o.join('');
}

Implementasi 4:

function reverse(s) {
  return s.split('').reverse().join('');
}

Implementasi 5:

function reverse(s) {
  var i = s.length,
      o = '';
  while (i > 0) {
    o += s.substring(i - 1, i);
    i--;
  }
  return o;
}

Implementasi 6:

function reverse(s) {
  for (var i = s.length - 1, o = ''; i >= 0; o += s[i--]) { }
  return o;
}

Implementasi 7:

function reverse(s) {
  return (s === '') ? '' : reverse(s.substr(1)) + s.charAt(0);
}

Implementasi 8:

function reverse(s) {
  function rev(s, len, o) {
    return (len === 0) ? o : rev(s, --len, (o += s[len]));
  };
  return rev(s, s.length, '');
}

Implementasi 9:

function reverse(s) {
  s = s.split('');
  var len = s.length,
      halfIndex = Math.floor(len / 2) - 1,
      tmp;


     for (var i = 0; i <= halfIndex; i++) {
        tmp = s[len - i - 1];
        s[len - i - 1] = s[i];
        s[i] = tmp;
      }
      return s.join('');
    }

Implementasi 10

function reverse(s) {
  if (s.length < 2)
    return s;
  var halfIndex = Math.ceil(s.length / 2);
  return reverse(s.substr(halfIndex)) +
         reverse(s.substr(0, halfIndex));
}

53

Seluruh "membalikkan string di tempat" adalah pertanyaan wawancara programmer C kuno, dan orang-orang yang diwawancarai oleh mereka (untuk balas dendam, mungkin?), Akan bertanya. Sayangnya, ini adalah bagian "Di Tempat" yang tidak lagi berfungsi karena string dalam hampir semua bahasa yang dikelola (JS, C #, dll) menggunakan string yang tidak dapat diubah, sehingga mengalahkan seluruh gagasan untuk memindahkan string tanpa mengalokasikan memori baru.

Sementara solusi di atas memang membalikkan string, mereka tidak melakukannya tanpa mengalokasikan lebih banyak memori, dan dengan demikian tidak memenuhi persyaratan. Anda harus memiliki akses langsung ke string yang dialokasikan, dan dapat memanipulasi lokasi memori aslinya untuk dapat membalikkannya di tempat.

Secara pribadi, saya benar-benar benci pertanyaan wawancara semacam ini, tetapi sayangnya, saya yakin kami akan terus melihatnya selama bertahun-tahun yang akan datang.


7
Paling tidak saya bisa mengatakan bahwa saya punya satu pewawancara beberapa waktu lalu sangat terkesan ketika dia bertanya kepada saya bagaimana membalikkan string "di tempat" di JS dan saya menjelaskan mengapa itu tidak mungkin karena string di JS tidak dapat diubah. Saya tidak tahu apakah itu jawaban yang dia harapkan atau apakah saya sedikit mendidiknya. Apa pun itu berhasil;)
Chev

1
Mungkin maksudnya "dikelola" oleh seorang pemulung, setidaknya itulah yang biasanya dimaksud dengan "bahasa yang dikelola" atau kehadiran Mesin Virtual / Lingkungan Runtime Virtual? @torazaburo
AntonB

39

Pertama, gunakan Array.from()untuk mengubah string menjadi array, lalu Array.prototype.reverse()membalikkan array, dan kemudian Array.prototype.join()membuatnya kembali menjadi string.

const reverse = str => Array.from(str).reverse().join('');

Ada overhead, tapi ini solusi yang elegan! Tidak ada penulisan ulang reverselogika yang sudah ada sebelumnya .
Gershom

2
@ Feliksbecker Tidak, string.split('')tidak bekerja. Lihat jawaban ini untuk penjelasan lebih lanjut.
Michał Perłakowski

5
Ini harus menjadi jawaban yang diterima karena ini juga bekerja dengan unicode. Misalnya, dari contoh di atas:Array.from('foo 𝌆 bar mañana mañana').reverse().join('') == 'anãnam anañam rab 𝌆 oof'
Julian TF

3
@JulianTF Tidak juga, satu tilde masih diterapkan pada 'a' bukan 'n'.
Roman Boiko

2
@ RomanBoiko Benar, tetapi Anda dapat menormalkan string terlebih dahulu. Array.from('foo 𝌆 bar mañana mañana'.normalize('NFC')).reverse().join('')akan menjadi"anañam anañam rab 𝌆 oof"
Mr Lister

26

Di ECMAScript 6, Anda dapat membalik string lebih cepat tanpa menggunakan .split('')metode split, dengan operator spread seperti:

var str = [...'racecar'].reverse().join('');

1
ES6 juga memungkinkan Anda untuk menggunakan dua backtick `` alih-alih('')

tidak ada alasan untuk menggunakan dua backticks dalam kasus ini
Vic

1
Kecuali Anda kode golf, Anda harus menghindari ini. Menulis string.split('')lebih jelas bagi kebanyakan orang daripada [...string].
AnnanFay

1
@AnnanFay .split('')memiliki masalah dengan karakter dari pesawat tambahan (pasangan pengganti dalam UTF-16), karena terbagi oleh unit kode UTF-16 daripada titik kode . Operator spread dan Array.from()(preferensi saya) tidak.
Inkling

@Inkling Saya tidak menyadari bahwa itu adalah masalah. Terima kasih telah menunjukkannya. Saya masih tergoda untuk menulis fungsi utilitas untuk kejelasan.
AnnanFay

19

Sepertinya saya terlambat 3 tahun ke pesta ...

Sayangnya Anda tidak bisa seperti yang telah ditunjukkan. Lihat Apakah string JavaScript tidak dapat diubah? Apakah saya memerlukan "pembuat string" dalam JavaScript?

Hal terbaik berikutnya yang dapat Anda lakukan adalah membuat "view" atau "wrapper", yang mengambil string dan menambahkan kembali bagian apa pun dari string API yang Anda gunakan, tetapi pura-pura string tersebut terbalik. Sebagai contoh:

var identity = function(x){return x};

function LazyString(s) {
    this.original = s;

    this.length = s.length;
    this.start = 0; this.stop = this.length; this.dir = 1; // "virtual" slicing
    // (dir=-1 if reversed)

    this._caseTransform = identity;
}

// syntactic sugar to create new object:
function S(s) {
    return new LazyString(s);
}

//We now implement a `"...".reversed` which toggles a flag which will change our math:

(function(){ // begin anonymous scope
    var x = LazyString.prototype;

    // Addition to the String API
    x.reversed = function() {
        var s = new LazyString(this.original);

        s.start = this.stop - this.dir;
        s.stop = this.start - this.dir;
        s.dir = -1*this.dir;
        s.length = this.length;

        s._caseTransform = this._caseTransform;
        return s;
    }

//We also override string coercion for some extra versatility (not really necessary):

    // OVERRIDE STRING COERCION
    //   - for string concatenation e.g. "abc"+reversed("abc")
    x.toString = function() {
        if (typeof this._realized == 'undefined') {  // cached, to avoid recalculation
            this._realized = this.dir==1 ?
                this.original.slice(this.start,this.stop) : 
                this.original.slice(this.stop+1,this.start+1).split("").reverse().join("");

            this._realized = this._caseTransform.call(this._realized, this._realized);
        }
        return this._realized;
    }

//Now we reimplement the String API by doing some math:

    // String API:

    // Do some math to figure out which character we really want

    x.charAt = function(i) {
        return this.slice(i, i+1).toString();
    }
    x.charCodeAt = function(i) {
        return this.slice(i, i+1).toString().charCodeAt(0);
    }

// Slicing functions:

    x.slice = function(start,stop) {
        // lazy chaining version of https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Array/slice

        if (stop===undefined)
            stop = this.length;

        var relativeStart = start<0 ? this.length+start : start;
        var relativeStop = stop<0 ? this.length+stop : stop;

        if (relativeStart >= this.length)
            relativeStart = this.length;
        if (relativeStart < 0)
            relativeStart = 0;

        if (relativeStop > this.length)
            relativeStop = this.length;
        if (relativeStop < 0)
            relativeStop = 0;

        if (relativeStop < relativeStart)
            relativeStop = relativeStart;

        var s = new LazyString(this.original);
        s.length = relativeStop - relativeStart;
        s.start = this.start + this.dir*relativeStart;
        s.stop = s.start + this.dir*s.length;
        s.dir = this.dir;

        //console.log([this.start,this.stop,this.dir,this.length], [s.start,s.stop,s.dir,s.length])

        s._caseTransform = this._caseTransform;
        return s;
    }
    x.substring = function() {
        // ...
    }
    x.substr = function() {
        // ...
    }

//Miscellaneous functions:

    // Iterative search

    x.indexOf = function(value) {
        for(var i=0; i<this.length; i++)
            if (value==this.charAt(i))
                return i;
        return -1;
    }
    x.lastIndexOf = function() {
        for(var i=this.length-1; i>=0; i--)
            if (value==this.charAt(i))
                return i;
        return -1;
    }

    // The following functions are too complicated to reimplement easily.
    // Instead just realize the slice and do it the usual non-in-place way.

    x.match = function() {
        var s = this.toString();
        return s.apply(s, arguments);
    }
    x.replace = function() {
        var s = this.toString();
        return s.apply(s, arguments);
    }
    x.search = function() {
        var s = this.toString();
        return s.apply(s, arguments);
    }
    x.split = function() {
        var s = this.toString();
        return s.apply(s, arguments);
    }

// Case transforms:

    x.toLowerCase = function() {
        var s = new LazyString(this.original);
        s._caseTransform = ''.toLowerCase;

        s.start=this.start; s.stop=this.stop; s.dir=this.dir; s.length=this.length;

        return s;
    }
    x.toUpperCase = function() {
        var s = new LazyString(this.original);
        s._caseTransform = ''.toUpperCase;

        s.start=this.start; s.stop=this.stop; s.dir=this.dir; s.length=this.length;

        return s;
    }

})() // end anonymous scope

Demo:

> r = S('abcABC')
LazyString
  original: "abcABC"
  __proto__: LazyString

> r.charAt(1);       // doesn't reverse string!!! (good if very long)
"B"

> r.toLowerCase()    // must reverse string, so does so
"cbacba"

> r.toUpperCase()    // string already reversed: no extra work
"CBACBA"

> r + '-demo-' + r   // natural coercion, string already reversed: no extra work
"CBAcba-demo-CBAcba"

Kicker - yang berikut dilakukan di tempat dengan matematika murni, mengunjungi setiap karakter hanya sekali, dan hanya jika perlu:

> 'demo: ' + S('0123456789abcdef').slice(3).reversed().slice(1,-1).toUpperCase()
"demo: EDCBA987654"

> S('0123456789ABCDEF').slice(3).reversed().slice(1,-1).toLowerCase().charAt(3)
"b"

Ini menghasilkan penghematan yang signifikan jika diterapkan pada string yang sangat besar, jika Anda hanya mengambil sepotong yang relatif kecil.

Apakah ini layak (lebih dari membalik-sebagai-salinan seperti di kebanyakan bahasa pemrograman) sangat tergantung pada kasus penggunaan Anda dan seberapa efisien Anda menerapkan kembali API string. Sebagai contoh jika semua yang Anda inginkan adalah melakukan manipulasi indeks string, atau mengambil slices atau substrs kecil, ini akan menghemat ruang dan waktu. Jika Anda berencana untuk mencetak irisan atau substring besar terbalik, penghematan mungkin memang kecil, bahkan lebih buruk daripada melakukan salinan lengkap. String "terbalik" Anda juga tidak akan memiliki tipe string, meskipun Anda mungkin bisa memalsukan ini dengan membuat prototipe.

Implementasi demo di atas membuat objek tipe ReversedString baru. Ini adalah prototipe, dan karenanya cukup efisien, dengan kerja yang hampir minimal dan overhead ruang minimal (definisi prototipe digunakan bersama). Ini adalah implementasi malas yang melibatkan pemotongan yang ditangguhkan. Setiap kali Anda melakukan fungsi seperti .sliceatau .reversed, itu akan melakukan indeks matematika. Akhirnya ketika Anda mengekstrak data (dengan menelepon .toString()atau.charCodeAt(...) atau sesuatu), akan menerapkan mereka dengan cara yang "pintar", menyentuh data paling mungkin.

Catatan: API string di atas adalah contoh, dan mungkin tidak diimplementasikan dengan sempurna. Anda juga dapat menggunakan hanya 1-2 fungsi yang Anda butuhkan.


13

Ada banyak cara Anda dapat membalikkan string dalam JavaScript. Saya mencatat tiga cara yang saya sukai.

Pendekatan 1: Menggunakan fungsi terbalik:

function reverse(str) {
  return str.split('').reverse().join('');
}

Pendekatan 2: Looping melalui karakter:

function reverse(str) {
  let reversed = '';

  for (let character of str) {
    reversed = character + reversed;
  }

  return reversed;
}

Pendekatan 3: Menggunakan fungsi pengurangan:

function reverse(str) {
  return str.split('').reduce((rev, char) => char + rev, '');
}

Saya harap ini membantu :)


10

Selama wawancara, saya diminta untuk membalik string tanpa menggunakan variabel atau metode asli. Ini adalah implementasi favorit saya:

function reverseString(str) {
    return str === '' ? '' : reverseString(str.slice(1)) + str[0];
}

Singkat, sederhana, tetapi lambat sekali;)
Tom

13
Metode nol asli? Bagaimana dengan slice? : - /
leaf

1
Penggunaan rekursi yang menarik. Ironisnya itu ada di Stack Overflow. stackoverflow.com/q/2805172/265877
Alex

@ Alex, Anda membuat poin yang bagus. Dalam beberapa kasus, pewawancara akan meminta Anda untuk tidak menggunakannya Array.prototype.reverse().
Daniel

10

Ada beberapa cara untuk melakukannya, Anda dapat memeriksa yang berikut,

1. Tradisional untuk loop (incrementing):

function reverseString(str){
        let stringRev ="";
        for(let i= 0; i<str.length; i++){
            stringRev = str[i]+stringRev;
        }
        return stringRev;
}
alert(reverseString("Hello World!"));

2. Tradisional untuk loop (decrementing):

function reverseString(str){
    let revstr = "";
    for(let i = str.length-1; i>=0; i--){
        revstr = revstr+ str[i];
    }
    return revstr;
}
alert(reverseString("Hello World!"));

3. Menggunakan for-of loop

function reverseString(str){
    let strn ="";
    for(let char of str){
        strn = char + strn;
    }
    return strn;
}
alert(reverseString("Get well soon"));

4. Menggunakan metode array forEach / pesanan tinggi:

function reverseString(str){

  let revSrring = "";
  str.split("").forEach(function(char){
    
    revSrring = char + revSrring;
  
  });
  return revSrring;
}
alert(reverseString("Learning JavaScript"));

5. standar ES6:

function reverseString(str){

  let revSrring = "";
  str.split("").forEach(char => revSrring = char + revSrring);
  return revSrring;
}
alert(reverseString("Learning JavaScript"));

6. Cara terbaru:

function reverseString(str){

  return str.split("").reduce(function(revString, char){
       return char + revString;
  }, "");
 
}

alert(reverseString("Learning JavaScript"));

7. Anda juga bisa mendapatkan hasilnya menggunakan yang berikut,

function reverseString(str){

  return str.split("").reduce((revString, char)=> char + revString, "");
 
}
alert(reverseString("Learning JavaScript"));


7

Di ES6, Anda memiliki satu opsi lagi

function reverseString (str) {
  return [...str].reverse().join('')
}

reverseString('Hello');

6

Ini adalah cara termudah yang saya pikirkan

var reverse = function(str) {
    var arr = [];
    
    for (var i = 0, len = str.length; i <= len; i++) {
        arr.push(str.charAt(len - i))
    }

    return arr.join('');
}

console.log(reverse('I want a 🍺'));


3
Sangat menyenangkan bahwa Anda memasukkan emoji dalam contoh Anda. Sehingga kita cepat melihat bahwa ini jelas tidak bekerja untuk emoji dan banyak karakter unicode lainnya.
Íhor Mé

Iman, sementara jawaban Anda benar, saya tidak setuju bahwa itu adalah cara termudah. Beberapa jawaban pertama memanfaatkan Array.prototype.reverse()itu akan menjadi cara termudah, karenanya jawaban yang paling populer. Tentu saja, itu membutuhkan pengetahuan sebelumnya tentang JavaScript.
Daniel

6
var str = 'sample string';
[].map.call(str, function(x) {
  return x;
}).reverse().join('');

ATAU

var str = 'sample string';
console.log(str.split('').reverse().join(''));

// Keluaran: 'gnirts elpmas'


Seluruh bagian 'peta' Anda dapat ditulis sebagai [...str].

5

Saya tahu bahwa ini adalah pertanyaan lama yang telah dijawab dengan baik, tetapi untuk hiburan saya sendiri, saya menulis fungsi terbalik berikut dan berpikir saya akan membagikannya jika itu bermanfaat bagi orang lain. Ini menangani kedua pasangan pengganti dan menggabungkan tanda:

function StringReverse (str)
{
  var charArray = [];
  for (var i = 0; i < str.length; i++)
    {
      if (i+1 < str.length)
        {
          var value = str.charCodeAt(i);
          var nextValue = str.charCodeAt(i+1);
          if (   (   value >= 0xD800 && value <= 0xDBFF
                  && (nextValue & 0xFC00) == 0xDC00) // Surrogate pair)
              || (nextValue >= 0x0300 && nextValue <= 0x036F)) // Combining marks
            {
              charArray.unshift(str.substring(i, i+2));
              i++; // Skip the other half
              continue;
            }
        }

      // Otherwise we just have a rogue surrogate marker or a plain old character.
      charArray.unshift(str[i]);
    }

  return charArray.join('');
}

Semua alat peraga untuk Mathias, Punycode, dan berbagai referensi lainnya untuk mendidik saya tentang kompleksitas pengkodean karakter dalam JavaScript.



3

Jika Anda tidak ingin menggunakan fungsi bawaan apa pun. Coba ini

var string = 'abcdefg';
var newstring = '';

for(let i = 0; i < string.length; i++){
    newstring = string[i] += newstring;
}

console.log(newstring);

2

Jawaban sebenarnya adalah: Anda tidak dapat membalikkannya di tempat, tetapi Anda dapat membuat string baru yang sebaliknya.

Sama seperti latihan untuk bermain dengan rekursi: kadang-kadang ketika Anda pergi ke sebuah wawancara, pewawancara mungkin bertanya kepada Anda bagaimana melakukan ini menggunakan rekursi, dan saya pikir "jawaban yang disukai" mungkin "Saya lebih suka tidak melakukan ini dalam rekursi karena itu dapat dengan mudah menyebabkan stack overflow "(karena itu O(n)bukan O(log n). Jika ya O(log n), cukup sulit untuk mendapatkan stack overflow - 4 miliar item dapat ditangani oleh level tumpukan 32, karena 2 ** 32 adalah 4294967296. Tetapi jika itu benarO(n) , maka itu bisa dengan mudah mendapatkan stack overflow.

Terkadang pewawancara masih akan bertanya kepada Anda, "sama seperti latihan, mengapa Anda tidak menulisnya menggunakan rekursi?" Dan ini dia:

String.prototype.reverse = function() {
    if (this.length <= 1) return this;
    else return this.slice(1).reverse() + this.slice(0,1);
}

uji coba:

var s = "";
for(var i = 0; i < 1000; i++) {
    s += ("apple" + i);
}
console.log(s.reverse());

keluaran:

999elppa899elppa...2elppa1elppa0elppa

Untuk mencoba mendapatkan stack overflow, saya beralih 1000ke 10000di Google Chrome, dan dilaporkan:

RangeError: Maximum call stack size exceeded

2

String sendiri tidak dapat diubah, tetapi Anda dapat dengan mudah membuat salinan terbalik dengan kode berikut:

function reverseString(str) {

  var strArray = str.split("");
  strArray.reverse();

  var strReverse = strArray.join("");

  return strReverse;
}

reverseString("hello");

2
//es6
//array.from
const reverseString = (string) => Array.from(string).reduce((a, e) => e + a);
//split
const reverseString = (string) => string.split('').reduce((a, e) => e + a); 

//split problem
"𠜎𠺢".split('')[0] === Array.from("𠜎𠺢")[0] // "�" === "𠜎" => false
"😂😹🤗".split('')[0] === Array.from("😂😹🤗")[0] // "�" === "😂" => false

1
Ini memiliki keuntungan bahwa ia menangani karakter bidang tambahan dengan benar.

2

Fungsi kecil yang menangani penggabungan diakritik dan karakter 2-byte:

(function(){
  var isCombiningDiacritic = function( code )
  {
    return (0x0300 <= code && code <= 0x036F)  // Comb. Diacritical Marks
        || (0x1AB0 <= code && code <= 0x1AFF)  // Comb. Diacritical Marks Extended
        || (0x1DC0 <= code && code <= 0x1DFF)  // Comb. Diacritical Marks Supplement
        || (0x20D0 <= code && code <= 0x20FF)  // Comb. Diacritical Marks for Symbols
        || (0xFE20 <= code && code <= 0xFE2F); // Comb. Half Marks

  };

  String.prototype.reverse = function()
  {
    var output = "",
        i      = this.length - 1,
        width;

    for ( ; i >= 0; --i )
    {
      width = 1;
      while( i > 0 && isCombiningDiacritic( this.charCodeAt(i) ) )
      {
        --i;
        width++;
      }

      if (
           i > 0
        && "\uDC00" <= this[i]   && this[i]   <= "\uDFFF"
        && "\uD800" <= this[i-1] && this[i-1] <= "\uDBFF"
      )
      {
        --i;
        width++;
      }

      output += this.substr( i, width );
    }

    return output;
  }
})();

// Tests
[
  'abcdefg',
  'ab\u0303c',
  'a\uD83C\uDFA5b',
  'a\uD83C\uDFA5b\uD83C\uDFA6c',
  'a\uD83C\uDFA5b\u0306c\uD83C\uDFA6d',
  'TO͇̹̺ͅƝ̴ȳ̳ TH̘Ë͖́̉ ͠P̯͍̭O̚​N̐Y̡' // copied from http://stackoverflow.com/a/1732454/1509264
].forEach(
  function(str){ console.log( str + " -> " + str.reverse() ); }
);
  


Memperbarui

Daftar yang lebih lengkap dari menggabungkan diakritik adalah:

      var isCombiningDiacritic = function( code )
      {
        return (0x0300 <= code && code <= 0x036F)
            || (0x0483 <= code && code <= 0x0489)
            || (0x0591 <= code && code <= 0x05BD)
            || (code == 0x05BF)
            || (0x05C1 <= code && code <= 0x05C2)
            || (0x05C4 <= code && code <= 0x05C5)
            || (code == 0x05C7)
            || (0x0610 <= code && code <= 0x061A)
            || (0x064B <= code && code <= 0x065F)
            || (code == 0x0670)
            || (0x06D6 <= code && code <= 0x06DC)
            || (0x06DF <= code && code <= 0x06E4)
            || (0x06E7 <= code && code <= 0x06E8)
            || (0x06EA <= code && code <= 0x06ED)
            || (code == 0x0711)
            || (0x0730 <= code && code <= 0x074A)
            || (0x07A6 <= code && code <= 0x07B0)
            || (0x07EB <= code && code <= 0x07F3)
            || (code == 0x07FD)
            || (0x0816 <= code && code <= 0x0819)
            || (0x081B <= code && code <= 0x0823)
            || (0x0825 <= code && code <= 0x0827)
            || (0x0829 <= code && code <= 0x082D)
            || (0x0859 <= code && code <= 0x085B)
            || (0x08D3 <= code && code <= 0x08E1)
            || (0x08E3 <= code && code <= 0x0902)
            || (code == 0x093A)
            || (code == 0x093C)
            || (0x0941 <= code && code <= 0x0948)
            || (code == 0x094D)
            || (0x0951 <= code && code <= 0x0957)
            || (0x0962 <= code && code <= 0x0963)
            || (code == 0x0981)
            || (code == 0x09BC)
            || (0x09C1 <= code && code <= 0x09C4)
            || (code == 0x09CD)
            || (0x09E2 <= code && code <= 0x09E3)
            || (0x09FE <= code && code <= 0x0A02)
            || (code == 0x0A3C)
            || (0x0A41 <= code && code <= 0x0A51)
            || (0x0A70 <= code && code <= 0x0A71)
            || (code == 0x0A75)
            || (0x0A81 <= code && code <= 0x0A82)
            || (code == 0x0ABC)
            || (0x0AC1 <= code && code <= 0x0AC8)
            || (code == 0x0ACD)
            || (0x0AE2 <= code && code <= 0x0AE3)
            || (0x0AFA <= code && code <= 0x0B01)
            || (code == 0x0B3C)
            || (code == 0x0B3F)
            || (0x0B41 <= code && code <= 0x0B44)
            || (0x0B4D <= code && code <= 0x0B56)
            || (0x0B62 <= code && code <= 0x0B63)
            || (code == 0x0B82)
            || (code == 0x0BC0)
            || (code == 0x0BCD)
            || (code == 0x0C00)
            || (code == 0x0C04)
            || (0x0C3E <= code && code <= 0x0C40)
            || (0x0C46 <= code && code <= 0x0C56)
            || (0x0C62 <= code && code <= 0x0C63)
            || (code == 0x0C81)
            || (code == 0x0CBC)
            || (0x0CCC <= code && code <= 0x0CCD)
            || (0x0CE2 <= code && code <= 0x0CE3)
            || (0x0D00 <= code && code <= 0x0D01)
            || (0x0D3B <= code && code <= 0x0D3C)
            || (0x0D41 <= code && code <= 0x0D44)
            || (code == 0x0D4D)
            || (0x0D62 <= code && code <= 0x0D63)
            || (code == 0x0DCA)
            || (0x0DD2 <= code && code <= 0x0DD6)
            || (code == 0x0E31)
            || (0x0E34 <= code && code <= 0x0E3A)
            || (0x0E47 <= code && code <= 0x0E4E)
            || (code == 0x0EB1)
            || (0x0EB4 <= code && code <= 0x0EBC)
            || (0x0EC8 <= code && code <= 0x0ECD)
            || (0x0F18 <= code && code <= 0x0F19)
            || (code == 0x0F35)
            || (code == 0x0F37)
            || (code == 0x0F39)
            || (0x0F71 <= code && code <= 0x0F7E)
            || (0x0F80 <= code && code <= 0x0F84)
            || (0x0F86 <= code && code <= 0x0F87)
            || (0x0F8D <= code && code <= 0x0FBC)
            || (code == 0x0FC6)
            || (0x102D <= code && code <= 0x1030)
            || (0x1032 <= code && code <= 0x1037)
            || (0x1039 <= code && code <= 0x103A)
            || (0x103D <= code && code <= 0x103E)
            || (0x1058 <= code && code <= 0x1059)
            || (0x105E <= code && code <= 0x1060)
            || (0x1071 <= code && code <= 0x1074)
            || (code == 0x1082)
            || (0x1085 <= code && code <= 0x1086)
            || (code == 0x108D)
            || (code == 0x109D)
            || (0x135D <= code && code <= 0x135F)
            || (0x1712 <= code && code <= 0x1714)
            || (0x1732 <= code && code <= 0x1734)
            || (0x1752 <= code && code <= 0x1753)
            || (0x1772 <= code && code <= 0x1773)
            || (0x17B4 <= code && code <= 0x17B5)
            || (0x17B7 <= code && code <= 0x17BD)
            || (code == 0x17C6)
            || (0x17C9 <= code && code <= 0x17D3)
            || (code == 0x17DD)
            || (0x180B <= code && code <= 0x180D)
            || (0x1885 <= code && code <= 0x1886)
            || (code == 0x18A9)
            || (0x1920 <= code && code <= 0x1922)
            || (0x1927 <= code && code <= 0x1928)
            || (code == 0x1932)
            || (0x1939 <= code && code <= 0x193B)
            || (0x1A17 <= code && code <= 0x1A18)
            || (code == 0x1A1B)
            || (code == 0x1A56)
            || (0x1A58 <= code && code <= 0x1A60)
            || (code == 0x1A62)
            || (0x1A65 <= code && code <= 0x1A6C)
            || (0x1A73 <= code && code <= 0x1A7F)
            || (0x1AB0 <= code && code <= 0x1B03)
            || (code == 0x1B34)
            || (0x1B36 <= code && code <= 0x1B3A)
            || (code == 0x1B3C)
            || (code == 0x1B42)
            || (0x1B6B <= code && code <= 0x1B73)
            || (0x1B80 <= code && code <= 0x1B81)
            || (0x1BA2 <= code && code <= 0x1BA5)
            || (0x1BA8 <= code && code <= 0x1BA9)
            || (0x1BAB <= code && code <= 0x1BAD)
            || (code == 0x1BE6)
            || (0x1BE8 <= code && code <= 0x1BE9)
            || (code == 0x1BED)
            || (0x1BEF <= code && code <= 0x1BF1)
            || (0x1C2C <= code && code <= 0x1C33)
            || (0x1C36 <= code && code <= 0x1C37)
            || (0x1CD0 <= code && code <= 0x1CD2)
            || (0x1CD4 <= code && code <= 0x1CE0)
            || (0x1CE2 <= code && code <= 0x1CE8)
            || (code == 0x1CED)
            || (code == 0x1CF4)
            || (0x1CF8 <= code && code <= 0x1CF9)
            || (0x1DC0 <= code && code <= 0x1DFF)
            || (0x20D0 <= code && code <= 0x20F0)
            || (0x2CEF <= code && code <= 0x2CF1)
            || (code == 0x2D7F)
            || (0x2DE0 <= code && code <= 0x2DFF)
            || (0x302A <= code && code <= 0x302D)
            || (0x3099 <= code && code <= 0x309A)
            || (0xA66F <= code && code <= 0xA672)
            || (0xA674 <= code && code <= 0xA67D)
            || (0xA69E <= code && code <= 0xA69F)
            || (0xA6F0 <= code && code <= 0xA6F1)
            || (code == 0xA802)
            || (code == 0xA806)
            || (code == 0xA80B)
            || (0xA825 <= code && code <= 0xA826)
            || (0xA8C4 <= code && code <= 0xA8C5)
            || (0xA8E0 <= code && code <= 0xA8F1)
            || (code == 0xA8FF)
            || (0xA926 <= code && code <= 0xA92D)
            || (0xA947 <= code && code <= 0xA951)
            || (0xA980 <= code && code <= 0xA982)
            || (code == 0xA9B3)
            || (0xA9B6 <= code && code <= 0xA9B9)
            || (0xA9BC <= code && code <= 0xA9BD)
            || (code == 0xA9E5)
            || (0xAA29 <= code && code <= 0xAA2E)
            || (0xAA31 <= code && code <= 0xAA32)
            || (0xAA35 <= code && code <= 0xAA36)
            || (code == 0xAA43)
            || (code == 0xAA4C)
            || (code == 0xAA7C)
            || (code == 0xAAB0)
            || (0xAAB2 <= code && code <= 0xAAB4)
            || (0xAAB7 <= code && code <= 0xAAB8)
            || (0xAABE <= code && code <= 0xAABF)
            || (code == 0xAAC1)
            || (0xAAEC <= code && code <= 0xAAED)
            || (code == 0xAAF6)
            || (code == 0xABE5)
            || (code == 0xABE8)
            || (code == 0xABED)
            || (code == 0xFB1E)
            || (0xFE00 <= code && code <= 0xFE0F)
            || (0xFE20 <= code && code <= 0xFE2F)
            || (code == 0x101FD)
            || (code == 0x102E0)
            || (0x10376 <= code && code <= 0x1037A)
            || (0x10A01 <= code && code <= 0x10A0F)
            || (0x10A38 <= code && code <= 0x10A3F)
            || (0x10AE5 <= code && code <= 0x10AE6)
            || (0x10D24 <= code && code <= 0x10D27)
            || (0x10F46 <= code && code <= 0x10F50)
            || (code == 0x11001)
            || (0x11038 <= code && code <= 0x11046)
            || (0x1107F <= code && code <= 0x11081)
            || (0x110B3 <= code && code <= 0x110B6)
            || (0x110B9 <= code && code <= 0x110BA)
            || (0x11100 <= code && code <= 0x11102)
            || (0x11127 <= code && code <= 0x1112B)
            || (0x1112D <= code && code <= 0x11134)
            || (code == 0x11173)
            || (0x11180 <= code && code <= 0x11181)
            || (0x111B6 <= code && code <= 0x111BE)
            || (0x111C9 <= code && code <= 0x111CC)
            || (0x1122F <= code && code <= 0x11231)
            || (code == 0x11234)
            || (0x11236 <= code && code <= 0x11237)
            || (code == 0x1123E)
            || (code == 0x112DF)
            || (0x112E3 <= code && code <= 0x112EA)
            || (0x11300 <= code && code <= 0x11301)
            || (0x1133B <= code && code <= 0x1133C)
            || (code == 0x11340)
            || (0x11366 <= code && code <= 0x11374)
            || (0x11438 <= code && code <= 0x1143F)
            || (0x11442 <= code && code <= 0x11444)
            || (code == 0x11446)
            || (code == 0x1145E)
            || (0x114B3 <= code && code <= 0x114B8)
            || (code == 0x114BA)
            || (0x114BF <= code && code <= 0x114C0)
            || (0x114C2 <= code && code <= 0x114C3)
            || (0x115B2 <= code && code <= 0x115B5)
            || (0x115BC <= code && code <= 0x115BD)
            || (0x115BF <= code && code <= 0x115C0)
            || (0x115DC <= code && code <= 0x115DD)
            || (0x11633 <= code && code <= 0x1163A)
            || (code == 0x1163D)
            || (0x1163F <= code && code <= 0x11640)
            || (code == 0x116AB)
            || (code == 0x116AD)
            || (0x116B0 <= code && code <= 0x116B5)
            || (code == 0x116B7)
            || (0x1171D <= code && code <= 0x1171F)
            || (0x11722 <= code && code <= 0x11725)
            || (0x11727 <= code && code <= 0x1172B)
            || (0x1182F <= code && code <= 0x11837)
            || (0x11839 <= code && code <= 0x1183A)
            || (0x119D4 <= code && code <= 0x119DB)
            || (code == 0x119E0)
            || (0x11A01 <= code && code <= 0x11A06)
            || (0x11A09 <= code && code <= 0x11A0A)
            || (0x11A33 <= code && code <= 0x11A38)
            || (0x11A3B <= code && code <= 0x11A3E)
            || (code == 0x11A47)
            || (0x11A51 <= code && code <= 0x11A56)
            || (0x11A59 <= code && code <= 0x11A5B)
            || (0x11A8A <= code && code <= 0x11A96)
            || (0x11A98 <= code && code <= 0x11A99)
            || (0x11C30 <= code && code <= 0x11C3D)
            || (0x11C92 <= code && code <= 0x11CA7)
            || (0x11CAA <= code && code <= 0x11CB0)
            || (0x11CB2 <= code && code <= 0x11CB3)
            || (0x11CB5 <= code && code <= 0x11CB6)
            || (0x11D31 <= code && code <= 0x11D45)
            || (code == 0x11D47)
            || (0x11D90 <= code && code <= 0x11D91)
            || (code == 0x11D95)
            || (code == 0x11D97)
            || (0x11EF3 <= code && code <= 0x11EF4)
            || (0x16AF0 <= code && code <= 0x16AF4)
            || (0x16B30 <= code && code <= 0x16B36)
            || (code == 0x16F4F)
            || (0x16F8F <= code && code <= 0x16F92)
            || (0x1BC9D <= code && code <= 0x1BC9E)
            || (0x1D167 <= code && code <= 0x1D169)
            || (0x1D17B <= code && code <= 0x1D182)
            || (0x1D185 <= code && code <= 0x1D18B)
            || (0x1D1AA <= code && code <= 0x1D1AD)
            || (0x1D242 <= code && code <= 0x1D244)
            || (0x1DA00 <= code && code <= 0x1DA36)
            || (0x1DA3B <= code && code <= 0x1DA6C)
            || (code == 0x1DA75)
            || (code == 0x1DA84)
            || (0x1DA9B <= code && code <= 0x1E02A)
            || (0x1E130 <= code && code <= 0x1E136)
            || (0x1E2EC <= code && code <= 0x1E2EF)
            || (0x1E8D0 <= code && code <= 0x1E8D6)
            || (0x1E944 <= code && code <= 0x1E94A)
            || (0xE0100 <= code && code <= 0xE01EF);
      };

Upaya yang layak, tetapi jika Anda memindai file UnicodeData.txt, Anda akan menemukan bahwa ada 316 rentang yang mengkombinasikan diakritik, daripada 5.
Mr Lister

@ Mr.Lister Solusinya kemudian adalah mengedit isCombiningDiacriticfungsi untuk memasukkan semua rentang 316; merasa bebas untuk memberikan suntingan itu karena Anda tampaknya memiliki data untuk diserahkan.
MT0

1
function reverseString(string) {
    var reversedString = "";
    var stringLength = string.length - 1;
    for (var i = stringLength; i >= 0; i--) {
        reversedString += string[i];
    }
    return reversedString;
}

1

tanpa mengubah string menjadi array;

String.prototype.reverse = function() {

    var ret = "";
    var size = 0;

    for (var i = this.length - 1; -1 < i; i -= size) {

        if (
          '\uD800' <= this[i - 1] && this[i - 1] <= '\uDBFF' && 
          '\uDC00' <= this[i]     && this[i]     <= '\uDFFF'
        ) {
            size = 2;
            ret += this[i - 1] + this[i];
        } else {
            size = 1;
            ret += this[i];
        }
    }

    return ret;
}

console.log('anãnam anañam' === 'mañana mañana'.reverse());

menggunakan Array.reverse tanpa mengkonversi karakter ke titik kode;

String.prototype.reverse = function() {

    var array = this.split("").reverse();

    for (var i = 0; i < this.length; ++i) {

        if (
          '\uD800' <= this[i - 1] && this[i - 1] <= '\uDBFF' && 
          '\uDC00' <= this[i]     && this[i]     <= '\uDFFF'
        ) {
            array[i - 1] = array[i - 1] + array[i];
            array[i] = array[i - 1].substr(0, 1);
            array[i - 1] = array[i - 1].substr(1, 1);
        }

    }

    return array.join("");
}

console.log('anãnam anañam' === 'mañana mañana'.reverse());

Untuk versi kedua: var c = array[i-1]; array[i-1] = array[i]; array[i] = c;tidak perlu menyatukan pasangan kode. Juga, for-loop harus dimulai pada 1.
MT0

Versi kedua tidak berfungsi '\ud83c\ud83c\udfa5'.reverse()- ini akan menghasilkan output yang sama dengan input. Menambahkan ++i;dalam ifpernyataan harus memperbaikinya.
MT0

Pada pemikiran kedua - ini tidak menangani menggabungkan diakritik: 'a\u0303bc'.reverse() === 'cba\u0303'harus mengembalikan true.
MT0

1

Saya pikir String.prototype.reverse adalah cara yang baik untuk menyelesaikan masalah ini; kode seperti di bawah ini;

String.prototype.reverse = function() {
  return this.split('').reverse().join('');
}

var str = 'this is a good example for string reverse';
str.reverse();
-> "esrever gnirts rof elpmaxe doog a si siht";

1

Menggunakan fungsi Array,

String.prototype.reverse = function(){
    return [].reduceRight.call(this, function(last, secLast){return last + secLast});
}

1
var str = "my name is saurabh ";
var empStr='',finalString='';
var chunk=[];
function reverse(str){
var i,j=0,n=str.length;
    for(i=0;i<n;++i){
        if(str[i]===' '){
            chunk[j]=empStr;
            empStr = '';
            j++;
        }else{
            empStr=empStr+str[i];
        }
    }
    for(var z=chunk.length-1;z>=0;z--){
        finalString = finalString +' '+ chunk[z];
        console.log(finalString);
    }
    return true;
}
reverse(str);

Bagaimana ini "di tempat" ??
Sudhansu Choudhary

1

Upaya asli saya sendiri ...

var str = "The Car";

function reverseStr(str) {
  var reversed = "";
  var len = str.length;
  for (var i = 1; i < (len + 1); i++) {  
    reversed += str[len - i];      
  }

  return reversed;
}

var strReverse = reverseStr(str);    
console.log(strReverse);
// "raC ehT"

http://jsbin.com/bujiwo/19/edit?js,console,output


1

Tetap kering dan konyol !!

function reverse(s){
let str = s;
var reverse = '';
for (var i=str.length;i>0;i--){

    var newstr = str.substring(0,i)
    reverse += newstr.substr(-1,1)
}
return reverse;
}

1

OK, cukup sederhana, Anda dapat membuat fungsi dengan loop sederhana untuk melakukan string terbalik untuk Anda tanpa menggunakan reverse(),charAt() dll seperti ini:

Misalnya Anda memiliki string ini:

var name = "StackOverflow";

Buat fungsi seperti ini, saya menyebutnya reverseString...

function reverseString(str) {
  if(!str.trim() || 'string' !== typeof str) {
    return;
  }
  let l=str.length, s='';
  while(l > 0) {
    l--;
    s+= str[l];
  }
  return s;
}

Dan Anda bisa menyebutnya seperti:

reverseString(name);

Dan hasilnya adalah:

"wolfrevOkcatS"

1

Cara terbaik untuk membalikkan string dalam JavaScript

1) Array.reverse:

Anda mungkin berpikir, tunggu dulu saya pikir kami membalikkan string, mengapa Anda menggunakan metode Array.reverse. Menggunakan metode String.split kami mengubah string kami menjadi Array karakter. Kemudian kita membalikkan urutan masing-masing nilai dalam array dan akhirnya kita mengubah Array kembali menjadi sebuah String menggunakan metode Array.join.

function reverseString(str) {
    return str.split('').reverse().join('');
}
reverseString('dwayne');

2) Pengurangan sementara-loop:

Meski cukup verbose, solusi ini memang memiliki kelebihan dibanding solusi satu. Anda tidak membuat array dan Anda hanya menyatukan string berdasarkan karakter dari string sumber.

Dari perspektif kinerja, yang satu ini mungkin akan menghasilkan hasil terbaik (meskipun belum diuji). Namun untuk string yang sangat panjang, keuntungan kinerja mungkin akan keluar dari jendela.

function reverseString(str) {
    var temp = '';
    var i = str.length;

    while (i > 0) {
        temp += str.substring(i - 1, i);
        i--;
    }


    return temp;
}
reverseString('dwayne');

3) Rekursi

Saya suka betapa sederhana dan jelasnya solusi ini. Anda dapat dengan jelas melihat bahwa metode String.charAt dan String.substr digunakan untuk melewati nilai yang berbeda dengan memanggil dirinya sendiri setiap kali hingga string kosong dimana ternary hanya akan mengembalikan string kosong daripada menggunakan rekursi untuk memanggil dirinya sendiri. . Ini mungkin akan menghasilkan kinerja terbaik kedua setelah solusi kedua.

function reverseString(str) {
    return (str === '') ? '' : reverseString(str.substr(1)) + str.charAt(0);
}
reverseString('dwayne');
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.