Konversikan camelCaseText ke Kalimat Teks Kasus


144

Bagaimana saya bisa mengonversi string seperti 'helloThere' atau 'HelloThere' menjadi 'Hello There' di JavaScript?


9
hmm .. berapa output yang Anda harapkan untuk iLiveInTheUSA?
wim

8
I Live In The ... oh sial! - Tetapi dalam kasus saya, saya memiliki serangkaian string terbatas dan tidak ada string yang dapat merusak konverter sederhana. Tangkapan yang bagus!
HyderA

Demikian pula, uSBPort akan menghasilkan "Port USB"
signonsridhar

2
@wim: iLiveInTheUSA harus iLiveInTheUsa dalam notasi kasus unta yang benar, tetapi itu akan menimbulkan masalah yang berbeda.
Konrad Höffner

Jawaban:


187
var text = 'helloThereMister';
var result = text.replace( /([A-Z])/g, " $1" );
var finalResult = result.charAt(0).toUpperCase() + result.slice(1);
console.log(finalResult);

huruf besar huruf pertama - sebagai contoh.

Perhatikan spasi di " $1".

EDIT: menambahkan contoh kapitalisasi huruf pertama. Tentu saja, kalau-kalau huruf pertama sudah modal - Anda akan memiliki ruang luang untuk menghapus.


1
Saya menggali penggunaan spasi di text.replace, saya telah memanggil fungsi padding dengan argumen 2+ dengan spasi untuk keterbacaan juga
rkd

8
uSBPorts => Port USB, bukan yang saya harapkan, saya ingin Port USB
signonsridhar

bagaimana dengan menulis suka Non-GoogleChrome?
tim

107

Atau menggunakan Lodash :

lodash.startCase(str);

Contoh:

_.startCase('helloThere');
// ➜ 'Hello There'

Lodash adalah pustaka yang bagus untuk memberikan pintasan ke banyak tugas js sehari-hari. Ada banyak fungsi manipulasi string serupa lainnya camelCase, seperti , kebabCasedll.


Jika Anda akan mencoba hello worldmaka output seharusnya Hello There, Dalam hal ini loadash tidak akan membantu.
Abhishek Kumar

@AbhishekKumar startCase dari Lodash akan benar-benar dikonversi hello worldke Hello World lodash.com/docs/4.17.15#upperFirst
user1696017

Anda benar bro. Secara tidak sengaja saya telah menulis surat hello therekepada hello world.
Abhishek Kumar

2
Setiap kali saya berpikir "tidak mungkin lodash melakukan ini juga", itu benar.
efru

Hati-hati pada v4 fungsi ini menghapus karakter khusus seperti ä dan mengubahnya menjadi yang ASCII (dalam hal ini)
collerek

52

Saya punya masalah serupa dan menanganinya seperti ini:

stringValue.replace(/([A-Z]+)*([A-Z][a-z])/g, "$1 $2")

Untuk solusi yang lebih kuat:

stringValue.replace(/([A-Z]+)/g, " $1").replace(/([A-Z][a-z])/g, " $1")

http://jsfiddle.net/PeYYQ/

Memasukkan:

 helloThere 
 HelloThere 
 ILoveTheUSA
 iLoveTheUSA

Keluaran:

 hello There 
 Hello There 
 I Love The USA
 i Love The USA

itu menempatkan ruang ekstra di awal
hannad rehman

4
Ini bukan kasus kalimat seperti yang diminta OP. Huruf pertama harus ditulis dengan huruf besar.
H Dog

Selain itu, ini menambahkan ruang ekstra di antara kata
Alacritas

34

Contohnya tanpa efek samping.

function camel2title(camelCase) {
  // no side-effects
  return camelCase
    // inject space before the upper case letters
    .replace(/([A-Z])/g, function(match) {
       return " " + match;
    })
    // replace first char with upper case
    .replace(/^./, function(match) {
      return match.toUpperCase();
    });
}

Dalam ES6

const camel2title = (camelCase) => camelCase
  .replace(/([A-Z])/g, (match) => ` ${match}`)
  .replace(/^./, (match) => match.toUpperCase());

1
Solid, +1 untuk cuplikan es6.
BradStell

4
FYI, ini menambah spasi kosong di awal kalimat.
Dale Zak

20

String terbaik yang saya temukan untuk menguji fungsi kasus unta-ke-judul-kasus adalah contoh yang sangat tidak masuk akal, yang menguji banyak kasing tepi. Sepengetahuan saya, tidak ada fungsi yang diposting sebelumnya menangani ini dengan benar :

ToGETYourGEDInTimeASongTentang 26ABCsIsOfTheEssenceTetapi, PersonalCard IDUntuk Pengguna456InRoom26PelatihanABC26Saat ini tidakMudahAs123ForC3POOrR2D2Or2R2D

Ini harus dikonversi menjadi:

Untuk Mendapatkan GED Anda Tepat Waktu Lagu tentang 26 ABC Penting, Tapi Kartu ID Pribadi Untuk Pengguna 456 Di Kamar 26A Berisi ABC 26 Kali Tidak Semudah 123 Untuk C3PO Atau R2D2 Atau 2R2D

Jika Anda menginginkan fungsi sederhana yang menangani kasus seperti di atas (dan lebih banyak kasus daripada banyak jawaban sebelumnya), inilah yang saya tulis. Kode ini tidak terlalu elegan atau cepat, tetapi sederhana, dapat dimengerti, dan berfungsi.

Contoh runnable online ada di jsfiddle , atau Anda dapat melihat output snippet di bawah ini di konsol Anda:

// Take a single camel case string and convert it to a string of separate words (with spaces) at the camel-case boundaries.
// 
// E.g.:
var examples = [
    'ToGetYourGEDInTimeASongAboutThe26ABCsIsOfTheEssenceButAPersonalIDCardForUser456InRoom26AContainingABC26TimesIsNotAsEasyAs123ForC3POOrR2D2Or2R2D',
    //                                          --> To Get Your GED In Time A Song About The 26 ABCs Is Of The Essence But A Personal ID Card For User 456 In Room 26A Containing ABC 26 Times Is Not As Easy As 123 For C3PO Or R2D2 Or 2R2D
    'helloThere', //                              --> Hello There
    'HelloThere', //                              --> Hello There
    'ILoveTheUSA', //                             --> I Love The USA
    'iLoveTheUSA', //                             --> I Love The USA
    'DBHostCountry', //                           --> DB Host Country
    'SetSlot123ToInput456', //                    --> Set Slot 123 To Input 456
    'ILoveTheUSANetworkInTheUSA', //              --> I Love The USA Network In The USA
    'Limit_IOC_Duration', //                      --> Limit IOC Duration
    'This_is_a_Test_of_Network123_in_12_days', // --> This Is A Test Of Network 123 In 12 Days
    'ASongAboutTheABCsIsFunToSing', //            --> A Song About The ABCs Is Fun To Sing
    'CFDs', //                                    --> CFDs
    'DBSettings', //                              --> DB Settings
    'IWouldLove1Apple', //                        --> 1 Would Love 1 Apple
    'Employee22IsCool', //                        --> Employee 22 Is Cool
    'SubIDIn', //                                 --> Sub ID In
    'ConfigureCFDsImmediately', //                --> Configure CFDs Immediately
    'UseTakerLoginForOnBehalfOfSubIDInOrders', // --> Use Taker Login For On Behalf Of Sub ID In Orders
]

function camelCaseToTitleCase(in_camelCaseString) {
        var result = in_camelCaseString                         // "ToGetYourGEDInTimeASongAboutThe26ABCsIsOfTheEssenceButAPersonalIDCardForUser456InRoom26AContainingABC26TimesIsNotAsEasyAs123ForC3POOrR2D2Or2R2D"
            .replace(/([a-z])([A-Z][a-z])/g, "$1 $2")           // "To Get YourGEDIn TimeASong About The26ABCs IsOf The Essence ButAPersonalIDCard For User456In Room26AContainingABC26Times IsNot AsEasy As123ForC3POOrR2D2Or2R2D"
            .replace(/([A-Z][a-z])([A-Z])/g, "$1 $2")           // "To Get YourGEDIn TimeASong About The26ABCs Is Of The Essence ButAPersonalIDCard For User456In Room26AContainingABC26Times Is Not As Easy As123ForC3POOr R2D2Or2R2D"
            .replace(/([a-z])([A-Z]+[a-z])/g, "$1 $2")          // "To Get Your GEDIn Time ASong About The26ABCs Is Of The Essence But APersonal IDCard For User456In Room26AContainingABC26Times Is Not As Easy As123ForC3POOr R2D2Or2R2D"
            .replace(/([A-Z]+)([A-Z][a-z][a-z])/g, "$1 $2")     // "To Get Your GEDIn Time A Song About The26ABCs Is Of The Essence But A Personal ID Card For User456In Room26A ContainingABC26Times Is Not As Easy As123ForC3POOr R2D2Or2R2D"
            .replace(/([a-z]+)([A-Z0-9]+)/g, "$1 $2")           // "To Get Your GEDIn Time A Song About The 26ABCs Is Of The Essence But A Personal ID Card For User 456In Room 26A Containing ABC26Times Is Not As Easy As 123For C3POOr R2D2Or 2R2D"
            
            // Note: the next regex includes a special case to exclude plurals of acronyms, e.g. "ABCs"
            .replace(/([A-Z]+)([A-Z][a-rt-z][a-z]*)/g, "$1 $2") // "To Get Your GED In Time A Song About The 26ABCs Is Of The Essence But A Personal ID Card For User 456In Room 26A Containing ABC26Times Is Not As Easy As 123For C3PO Or R2D2Or 2R2D"
            .replace(/([0-9])([A-Z][a-z]+)/g, "$1 $2")          // "To Get Your GED In Time A Song About The 26ABCs Is Of The Essence But A Personal ID Card For User 456In Room 26A Containing ABC 26Times Is Not As Easy As 123For C3PO Or R2D2Or 2R2D"  

            // Note: the next two regexes use {2,} instead of + to add space on phrases like Room26A and 26ABCs but not on phrases like R2D2 and C3PO"
            .replace(/([A-Z]{2,})([0-9]{2,})/g, "$1 $2")        // "To Get Your GED In Time A Song About The 26ABCs Is Of The Essence But A Personal ID Card For User 456 In Room 26A Containing ABC 26 Times Is Not As Easy As 123 For C3PO Or R2D2 Or 2R2D"
            .replace(/([0-9]{2,})([A-Z]{2,})/g, "$1 $2")        // "To Get Your GED In Time A Song About The 26 ABCs Is Of The Essence But A Personal ID Card For User 456 In Room 26A Containing ABC 26 Times Is Not As Easy As 123 For C3PO Or R2D2 Or 2R2D"
            .trim();


  // capitalize the first letter
  return result.charAt(0).toUpperCase() + result.slice(1);
}

examples.forEach(str => console.log(str, ' --> \n', camelCaseToTitleCase(str)));


11

Berdasarkan salah satu contoh di atas saya datang dengan ini:

const camelToTitle = (camelCase) => camelCase
  .replace(/([A-Z])/g, (match) => ` ${match}`)
  .replace(/^./, (match) => match.toUpperCase())
  .trim()

Ini bekerja untuk saya karena digunakan .trim()untuk menangani kasus tepi di mana huruf pertama ditulis dengan huruf kapital dan Anda berakhir dengan ruang tambahan terkemuka.

Referensi: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/Trim


10

Ok, saya beberapa tahun terlambat ke permainan, tapi saya punya pertanyaan serupa, dan saya ingin membuat solusi satu-ganti untuk setiap input yang mungkin. Saya harus memberikan sebagian besar kredit kepada @ ZenMaster di utas ini dan @Benjamin Udink ten Cate di utas ini . Berikut kodenya:

var camelEdges = /([A-Z](?=[A-Z][a-z])|[^A-Z](?=[A-Z])|[a-zA-Z](?=[^a-zA-Z]))/g;
var textArray = ["lowercase",
                 "Class",
                 "MyClass",
                 "HTML",
                 "PDFLoader",
                 "AString",
                 "SimpleXMLParser",
                 "GL11Version",
                 "99Bottles",
                 "May5",
                 "BFG9000"];
var text;
var resultArray = [];
for (var i = 0; i < a.length; i++){
    text = a[i];
    text = text.replace(camelEdges,'$1 ');
    text = text.charAt(0).toUpperCase() + text.slice(1);
    resultArray.push(text);
}

Ini memiliki tiga klausa, semua menggunakan lookahead untuk mencegah mesin regex dari mengkonsumsi terlalu banyak karakter:

  1. [A-Z](?=[A-Z][a-z])mencari huruf kapital yang diikuti dengan huruf kapital kemudian huruf kecil. Ini untuk mengakhiri akronim seperti AS.
  2. [^A-Z](?=[A-Z])mencari huruf kapital diikuti huruf kapital. Ini mengakhiri kata-kata seperti myWord dan simbol seperti 99Bottles.
  3. [a-zA-Z](?=[^a-zA-Z])mencari surat diikuti oleh bukan huruf. Ini mengakhiri kata sebelum simbol seperti BFG9000.

Pertanyaan ini ada di bagian atas hasil pencarian saya, jadi semoga saya dapat menghemat waktu orang lain!


9

Ini versi saya. Itu menambahkan spasi sebelum setiap huruf bahasa Inggris huruf besar yang datang setelah huruf bahasa Inggris huruf kecil dan juga huruf kapital huruf pertama jika diperlukan:

Sebagai contoh:
thisIsCamelCase -> Ini Adalah Kasus Unta
IsCamelCase -> Ini Ini Kasus Unta
thisIsCamelCase123 -> Ini Adalah Unta Case123

  function camelCaseToTitleCase(camelCase){
    if (camelCase == null || camelCase == "") {
      return camelCase;
    }

    camelCase = camelCase.trim();
    var newText = "";
    for (var i = 0; i < camelCase.length; i++) {
      if (/[A-Z]/.test(camelCase[i])
          && i != 0
          && /[a-z]/.test(camelCase[i-1])) {
        newText += " ";
      }
      if (i == 0 && /[a-z]/.test(camelCase[i]))
      {
        newText += camelCase[i].toUpperCase();
      } else {
        newText += camelCase[i];
      }
    }

    return newText;
  }

6

Implementasi ini mempertimbangkan huruf besar dan angka berturut-turut.

function camelToTitleCase(str) {
  return str
    .replace(/[0-9]{2,}/g, match => ` ${match} `)
    .replace(/[^A-Z0-9][A-Z]/g, match => `${match[0]} ${match[1]}`)
    .replace(/[A-Z][A-Z][^A-Z0-9]/g, match => `${match[0]} ${match[1]}${match[2]}`)
    .replace(/[ ]{2,}/g, match => ' ')
    .replace(/\s./g, match => match.toUpperCase())
    .replace(/^./, match => match.toUpperCase())
    .trim();
}

// ----------------------------------------------------- //

var testSet = [
    'camelCase',
    'camelTOPCase',
    'aP2PConnection',
    'superSimpleExample',
    'aGoodIPAddress',
    'goodNumber90text',
    'bad132Number90text',
];

testSet.forEach(function(item) {
    console.log(item, '->', camelToTitleCase(item));
});

Output yang diharapkan:

camelCase -> Camel Case
camelTOPCase -> Camel TOP Case
aP2PConnection -> A P2P Connection
superSimpleExample -> Super Simple Example
aGoodIPAddress -> A Good IP Address
goodNumber90text -> Good Number 90 Text
bad132Number90text -> Bad 132 Number 90 Text

Saya akan menggunakan jawaban Chris Kline yang mengakomodasi string seperti "Alamat IP" (di mana fungsi ini mengubahnya menjadi "Alamat IP"
John Hamm

@JohnHamm Input Anda adalah "Alamat IP", kan? Ini bukan kasus unta! Baca tentang wadah unta di sini: en.wikipedia.org/wiki/Camel_case Jangan letakkan spasi di antara dan masukan "IPAddress" saja. Fungsi ini berfungsi dengan baik.
Dipu

3

Anda dapat menggunakan fungsi seperti ini:

function fixStr(str) {
    var out = str.replace(/^\s*/, "");  // strip leading spaces
    out = out.replace(/^[a-z]|[^\s][A-Z]/g, function(str, offset) {
        if (offset == 0) {
            return(str.toUpperCase());
        } else {
            return(str.substr(0,1) + " " + str.substr(1).toUpperCase());
        }
    });
    return(out);
}

"hello World" ==> "Hello World"
"HelloWorld" ==> "Hello World"
"FunInTheSun" ==? "Fun In The Sun"

Kode dengan sekelompok string tes di sini: http://jsfiddle.net/jfriend00/FWLuV/ .

Versi alternatif yang membuat spasi di sini: http://jsfiddle.net/jfriend00/Uy2ac/ .


Saya tahu itu bukan persyaratan dalam pertanyaan, tetapi solusi Anda tidak berhasil " helloWorld", misalnya.
ZenMaster

Yap, itu persyaratan baru. Saya mencoba melakukan persis apa yang semula Anda minta. Pokoknya, jalan pintas mudah untuk menetapkan ruang terkemuka jika Anda tidak membutuhkannya di sana. Jika Anda ingin mereka tetap di tempatnya, itu bisa dilakukan juga.
jfriend00

Berikut adalah jsFiddle yang menunjukkan metode yang berfungsi dengan kebutuhan baru "helloWorld" dan mempertahankan ruang terdepan (jika Anda menginginkannya): jsfiddle.net/jfriend00/Uy2ac .
jfriend00

Bagus. Saya bertanya-tanya tentang kinerja itu. Fungsi pawang akan dipanggil pada setiap pertandingan, bukan?
ZenMaster

Jika Anda melakukan banyak sekali hal ini dalam pengaturan yang sensitif terhadap kinerja, akan dibutuhkan beberapa pengujian jsperf di banyak browser untuk melihat solusi apa yang paling cepat. Memanggil panggilan balik bukan masalah besar. Ekspresi reguler, dalam bentuk apa pun, jarang merupakan solusi tercepat vs kode tujuan khusus, tetapi mereka menyimpan banyak kode (dan seringkali beberapa bug) jadi sering kali merupakan pilihan yang diinginkan. Itu tergantung pada kebutuhan Anda.
jfriend00

3

coba perpustakaan ini

http://sugarjs.com/api/String/titleize

'man from the boondocks'.titleize()>"Man from the Boondocks"
'x-men: the last stand'.titleize()>"X Men: The Last Stand"
'TheManWithoutAPast'.titleize()>"The Man Without a Past"
'raiders_of_the_lost_ark'.titleize()>"Raiders of the Lost Ark"

2

Tidak ada jawaban di atas yang cocok untuk saya, jadi harus datang dengan sepeda sendiri:

function camelCaseToTitle(camelCase) {
    if (!camelCase) {
        return '';
    }

    var pascalCase = camelCase.charAt(0).toUpperCase() + camelCase.substr(1);
    return pascalCase
        .replace(/([a-z])([A-Z])/g, '$1 $2')
        .replace(/([A-Z])([A-Z][a-z])/g, '$1 $2')
        .replace(/([a-z])([0-9])/gi, '$1 $2')
        .replace(/([0-9])([a-z])/gi, '$1 $2');
}

Kasus uji:

null => ''
'' => ''
'simpleString' => 'Simple String'
'stringWithABBREVIATIONInside => 'String With ABBREVIATION Inside'
'stringWithNumber123' => 'String With Number 123'
'complexExampleWith123ABBR890Etc' => 'Complex Example With 123 ABBR 890 Etc'

2

Ini berfungsi untuk saya lihat ini

CamelcaseToWord ("MyName"); // kembalikan Nama Saya

    function CamelcaseToWord(string){
      return string.replace(/([A-Z]+)/g, " $1").replace(/([A-Z][a-z])/g, " $1");
    }

1
Selamat datang di SO :) Harap tambahkan setidaknya satu baris penjelasan ke kode Anda. Juga pastikan itu adalah karya intelektual Anda atau mengutip sumbernya.
Lorenz Lo Sauer

Anda harus menghapus spasi dalam lat "$ 1". string.replace(/([A-Z]+)/g, " $1").replace(/([A-Z][a-z])/g, "$1");
Valeria Shpiner

2

Saya pikir ini bisa dilakukan hanya dengan reg exp /([a-z]|[A-Z]+)([A-Z])/gdan penggantian "$1 $2".

ILoveTheUSADope -> I Love The USA Dope


Tidak juga, untuk string QWERTYyang dikembalikan QWERT Y.
itachi

2

Jika Anda berurusan dengan Capital Camel Case , snippet ini dapat membantu Anda, juga berisi beberapa spesifikasi sehingga Anda dapat yakin bahwa itu cocok dengan kasus Anda.

export const fromCamelCaseToSentence = (word) =>
  word
    .replace(/([A-Z][a-z]+)/g, ' $1')
    .replace(/([A-Z]{2,})/g, ' $1')
    .replace(/\s{2,}/g, ' ')
    .trim();

Dan spesifikasi:

describe('fromCamelCaseToSentence', () => {
 test('does not fall with a single word', () => {
   expect(fromCamelCaseToSentence('Approved')).toContain('Approved')
   expect(fromCamelCaseToSentence('MDA')).toContain('MDA')
 })

 test('does not fall with an empty string', () => {
   expect(fromCamelCaseToSentence('')).toContain('')
 })

 test('returns the separated by space words', () => {
   expect(fromCamelCaseToSentence('NotApprovedStatus')).toContain('Not Approved Status')
   expect(fromCamelCaseToSentence('GDBState')).toContain('GDB State')
   expect(fromCamelCaseToSentence('StatusDGG')).toContain('Status DGG')
 })
})

1

Saya tidak mencoba jawaban semua orang, tetapi beberapa solusi yang saya mainkan tidak cocok dengan semua persyaratan saya.

Saya dapat menemukan sesuatu yang ...

export const jsObjToCSSString = (o={}) =>
    Object.keys(o)
          .map(key => ({ key, value: o[key] }))
          .map(({key, value}) =>
              ({
                key: key.replace( /([A-Z])/g, "-$1").toLowerCase(),
                value
              })
          )
          .reduce(
              (css, {key, value}) => 
                  `${css} ${key}: ${value}; `.trim(), 
              '')

1

Di bawah ini adalah tautan yang menunjukkan string unta ke string kalimat menggunakan regex.

Memasukkan

myCamelCaseSTRINGToSPLITDemo

Keluaran

my Camel Case STRING To SPLIT Demo


Ini adalah regex untuk konversi case unta ke teks kalimat

(?=[A-Z][a-z])|([A-Z]+)([A-Z][a-rt-z][a-z]\*)

dengan $1 $2sebagai subtitusi.

Klik untuk melihat konversi pada regex


Berikan konten yang relevan dari tautan Anda di tubuh jawaban Anda.
Grant Miller

1

Masukkan javaScript

Output Java Script

   var text = 'javaScript';
    text.replace(/([a-z])([A-Z][a-z])/g, "$1 $2").charAt(0).toUpperCase()+text.slice(1).replace(/([a-z])([A-Z][a-z])/g, "$1 $2");

1

Satu lagi solusi berdasarkan RegEx.

respace(str) {
  const regex = /([A-Z])(?=[A-Z][a-z])|([a-z])(?=[A-Z])/g;
  return str.replace(regex, '$& ');
}

Penjelasan

RegEx di atas terdiri dari dua bagian serupa yang dipisahkan oleh operator OR . Paruh pertama:

  1. ([A-Z]) - cocok dengan huruf besar ...
  2. (?=[A-Z][a-z]) - Diikuti dengan urutan huruf besar dan kecil.

Ketika diterapkan pada urutan FOo , ini secara efektif cocok dengan huruf F -nya .

Atau skenario kedua:

  1. ([a-z]) - cocok dengan huruf kecil ...
  2. (?=[A-Z]) - Diikuti dengan huruf besar.

Ketika diterapkan ke barFoo urutan , ini secara efektif cocok dengan huruf r .

Ketika semua kandidat pengganti ditemukan, hal terakhir yang harus dilakukan adalah mengganti mereka dengan huruf yang sama tetapi dengan karakter spasi tambahan. Untuk ini, kita dapat menggunakan '$& 'sebagai pengganti, dan itu akan menyelesaikan untuk substring yang cocok diikuti oleh karakter spasi.

Contoh

const regex = /([A-Z])(?=[A-Z][a-z])|([a-z])(?=[A-Z])/g
const testWords = ['ACoolExample', 'fooBar', 'INAndOUT', 'QWERTY', 'fooBBar']

testWords.map(w => w.replace(regex, '$& '))
->(5) ["A Cool Example", "foo Bar", "IN And OUT", "QWERTY", "foo B Bar"]

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.