1773

String.StartsWithJavaScriptで C# に相当するものをどのように記述しますか?

var haystack = 'hello world';
var needle = 'he';

haystack.startsWith(needle) == true

注: これは古い質問であり、コメントで指摘されているように、ECMAScript 2015 (ES6) でこの.startsWithメソッドが導入されました。ただし、この更新 (2015) の執筆時点では、ブラウザーのサポートは完全にはほど遠いです。

4

19 に答える 19

1838

ECMAScript 6 のString.prototype.startsWith()メソッドを使用できますが、まだすべてのブラウザーでサポートされているわけではありません。シム/ポリフィルを使用して、それをサポートしていないブラウザーに追加することをお勧めします。仕様に記載されているすべての詳細に準拠する実装を作成するのは少し複雑です。忠実なシムが必要な場合は、次のいずれかを使用します。

メソッドを shimmed したら (または、既にそれを持っているブラウザーと JavaScript エンジンのみをサポートしている場合)、次のように使用できます。

   console.log("Hello World!".startsWith("He")); // true
    
var haystack = "Hello world";
var prefix = 'orl';
console.log(haystack.startsWith(prefix)); // false

于 2009-03-14T20:19:13.077 に答える
1305

別の代替手段.lastIndexOf

haystack.lastIndexOf(needle, 0) === 0

これは、 のインデックスから始まるのhaystackオカレンスを後方に検索します。つまり、で始まるかどうかのみをチェックします。needle0haystackhaystackneedle

原則として、これには他のいくつかのアプローチよりもパフォーマンス上の利点があります。

  • 全体を検索するわけではありませんhaystack
  • 新しい一時文字列を作成してすぐに破棄することはありません。
于 2011-01-02T16:14:42.457 に答える
598
data.substring(0, input.length) === input
于 2009-03-14T20:14:12.107 に答える
186

ヘルパー関数なしで、正規表現の.testメソッドを使用するだけです:

/^He/.test('Hello world')

ハードコードされた文字列ではなく動的文字列でこれを行うには (文字列に正規表現制御文字が含まれていないと仮定します):

new RegExp('^' + needle).test(haystack)

Is there a RegExp.escape function in Javascript?を確認してください。正規表現制御文字が文字列に現れる可能性がある場合。

于 2011-01-04T00:59:29.600 に答える
72

最善の解決策:

function startsWith(str, word) {
    return str.lastIndexOf(word, 0) === 0;
}

また、endWithも必要な場合は次のとおりです。

function endsWith(str, word) {
    return str.indexOf(word, str.length - word.length) !== -1;
}

それを文字列にプロトタイプすることを好む人のために:

String.prototype.startsWith || (String.prototype.startsWith = function(word) {
    return this.lastIndexOf(word, 0) === 0;
});

String.prototype.endsWith   || (String.prototype.endsWith = function(word) {
    return this.indexOf(word, this.length - word.length) !== -1;
});

使用法:

"abc".startsWith("ab")
true
"c".ensdWith("c") 
true

メソッドを使用:

startsWith("aaa", "a")
true
startsWith("aaa", "ab")
false
startsWith("abc", "abc")
true
startsWith("abc", "c")
false
startsWith("abc", "a")
true
startsWith("abc", "ba")
false
startsWith("abc", "ab")
true
于 2016-04-26T21:56:14.360 に答える
40

以下は、CMS のソリューションに対する小さな改善点です。

if(!String.prototype.startsWith){
    String.prototype.startsWith = function (str) {
        return !this.indexOf(str);
    }
}

"Hello World!".startsWith("He"); // true

 var data = "Hello world";
 var input = 'He';
 data.startsWith(input); // true

将来のブラウザーがネイティブ コードで実装する場合、または別のライブラリによって実装される場合に備えて、関数が既に存在するかどうかを確認します。たとえば、Prototype Library はこの関数を既に実装しています。

を使用すると、読みにくい!場合よりもわずかに高速で簡潔になります。=== 0

于 2009-05-27T02:54:51.353 に答える
21

underscore.string.jsもチェックしてください。メソッドを含む、一連の便利な文字列テストおよび操作メソッドが付属していますstartsWith。ドキュメントから:

で始まる _.startsWith(string, starts)

stringこのメソッドは、で始まるかどうかをチェックしstartsます。

_("image.gif").startsWith("image")
=> true
于 2011-05-31T18:29:50.940 に答える
11

これは非常に人気があるため、ECMA 6 にはこのメソッドの実装があり、その準備として、将来の問題や破損を防ぐために「公式」ポリフィルを使用する必要があることを指摘する価値があると思います。

幸いなことに、Mozilla の専門家が 1 つ提供してくれます。

https://developer.mozilla.org/de/docs/Web/JavaScript/Reference/Global_Objects/String/startsWith

if (!String.prototype.startsWith) {
    String.prototype.startsWith = function(searchString, position) {
        position = position || 0;
        return this.indexOf(searchString, position) === position;
    };
}

これには、ECMA 6 への移行時に適切に無視されるという利点があることに注意してください。

于 2016-01-05T11:34:05.247 に答える
5

最適なパフォーマンスの解決策は、ライブラリ呼び出しの使用をやめて、2 つの配列で作業していることを認識することです。手巻きの実装は短く、ここで見た他のどのソリューションよりも高速です。

function startsWith2(str, prefix) {
    if (str.length < prefix.length)
        return false;
    for (var i = prefix.length - 1; (i >= 0) && (str[i] === prefix[i]); --i)
        continue;
    return i < 0;
}

パフォーマンスの比較 (成功と失敗) については、http://jsperf.com/startswith2/4を参照してください。(私のものを打ち負かした可能性のある新しいバージョンを確認してください。)

于 2014-07-15T01:39:46.940 に答える
3
  1. 質問は少し古いですが、ここで提供されたすべての回答と Jim Buck によって共有された jsperf に基づいて作成したベンチマークを示すために、この回答を書きたいと思いました。

私は基本的に、長い針が長い干し草の山の中にあるかどうか、最後の文字を除いて非常に似ているかどうかをすばやく見つける方法が必要でした。

これは私が書いたコードで、各関数 (splice、substring、startsWith など) に対して、1.000.0001 文字の干し草の山文字列 ( nestedString) と 1.000.000 の偽または真実の針文字列に対して false と true を返す場合の両方をテストします。文字 (testParentStringFalseおよびtestParentStringTrue、それぞれ):

// nestedString is made of 1.000.001 '1' repeated characters.
var nestedString = '...'

// testParentStringFalse is made of 1.000.000 characters,
// all characters are repeated '1', but the last one is '2',
// so for this string the test should return false.
var testParentStringFalse = '...'

// testParentStringTrue is made of 1.000.000 '1' repeated characters,
// so for this string the test should return true.
var testParentStringTrue = '...'

// You can make these very long strings by running the following bash command
// and edit each one as needed in your editor
// (NOTE: on OS X, `pbcopy` copies the string to the clipboard buffer,
//        on Linux, you would probably need to replace it with `xclip`):
// 
//     printf '1%.0s' {1..1000000} | pbcopy
// 

function testString() {
    let dateStart
    let dateEnd
    let avg
    let count = 100000
    const falseResults = []
    const trueResults = []

    /* slice */
    console.log('========> slice')
    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.slice(0, testParentStringFalse.length) === testParentStringFalse
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    falseResults[falseResults.length] = {
        label: 'slice',
        avg
    }
    console.log(`testString() slice = false`, res, 'avg: ' + avg + 'ms')

    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.slice(0, testParentStringTrue.length) === testParentStringTrue
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    trueResults[trueResults.length] = {
        label: 'slice',
        avg
    }
    console.log(`testString() slice = true`, res, 'avg: ' + avg + 'ms')
    console.log('<======== slice')
    console.log('')
    /* slice END */

    /* lastIndexOf */
    console.log('========> lastIndexOf')
    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.lastIndexOf(testParentStringFalse, 0) === 0
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    falseResults[falseResults.length] = {
        label: 'lastIndexOf',
        avg
    }
    console.log(`testString() lastIndexOf = false`, res, 'avg: ' + avg + 'ms')

    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.lastIndexOf(testParentStringTrue, 0) === 0
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    trueResults[trueResults.length] = {
        label: 'lastIndexOf',
        avg
    }
    console.log(`testString() lastIndexOf = true`, res, 'avg: ' + avg + 'ms')
    console.log('<======== lastIndexOf')
    console.log('')
    /* lastIndexOf END */

    /* indexOf */
    console.log('========> indexOf')
    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.indexOf(testParentStringFalse) === 0
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    falseResults[falseResults.length] = {
        label: 'indexOf',
        avg
    }
    console.log(`testString() indexOf = false`, res, 'avg: ' + avg + 'ms')

    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.indexOf(testParentStringTrue) === 0
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    trueResults[trueResults.length] = {
        label: 'indexOf',
        avg
    }
    console.log(`testString() indexOf = true`, res, 'avg: ' + avg + 'ms')
    console.log('<======== indexOf')
    console.log('')
    /* indexOf END */

    /* substring */
    console.log('========> substring')
    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.substring(0, testParentStringFalse.length) === testParentStringFalse
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    falseResults[falseResults.length] = {
        label: 'substring',
        avg
    }
    console.log(`testString() substring = false`, res, 'avg: ' + avg + 'ms')

    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.substring(0, testParentStringTrue.length) === testParentStringTrue
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    trueResults[trueResults.length] = {
        label: 'substring',
        avg
    }
    console.log(`testString() substring = true`, res, 'avg: ' + avg + 'ms')
    console.log('<======== substring')
    console.log('')
    /* substring END */

    /* startsWith */
    console.log('========> startsWith')
    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.startsWith(testParentStringFalse)
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    falseResults[falseResults.length] = {
        label: 'startsWith',
        avg
    }
    console.log(`testString() startsWith = false`, res, 'avg: ' + avg + 'ms')

    dateStart = +new Date()
    var res
    for (let j = 0; j < count; j++) {
        res = nestedString.startsWith(testParentStringTrue)
    }
    dateEnd = +new Date()
    avg = (dateEnd - dateStart)/count
    trueResults[trueResults.length] = {
        label: 'startsWith',
        avg
    }
    console.log(`testString() startsWith = true`, res, 'avg: ' + avg + 'ms')
    console.log('<======== startsWith')
    console.log('')
    /* startsWith END */

    falseResults.sort((a, b) => a.avg - b.avg)
    trueResults.sort((a, b) => a.avg - b.avg)

    console.log('false results from fastest to slowest avg:', falseResults)
    console.log('true results from fastest to slowest avg:', trueResults)
}

このベンチマーク テストは、Chrome 75Firefox 67Safari 12Opera 62で実行しました。

Edge と IE はこのマシンにないので含めていませんが、誰かが Edge と少なくとも IE 9 に対してスクリプトを実行し、ここで出力を共有したい場合は、結果を見てみたいと思います.

3 つの長い文字列を再作成し、スクリプトをファイルに保存する必要があることを覚えておいてください。各文字列の長さが 1.000.000 以上であるため、ブラウザーのコンソールでコピー/貼り付けを行うとブロックされます)。

出力は次のとおりです。

クロム 75 (substring勝利):

false results from fastest to slowest avg:
1)  {"label":"substring","avg":0.08271}
2)  {"label":"slice","avg":0.08615}
3)  {"label":"lastIndexOf","avg":0.77025}
4)  {"label":"indexOf","avg":1.64375}
5)  {"label":"startsWith","avg":3.5454}

true results from fastest to slowest avg:
1)  {"label":"substring","avg":0.08213}
2)  {"label":"slice","avg":0.08342}
3)  {"label":"lastIndexOf","avg":0.7831}
4)  {"label":"indexOf","avg":0.88988}
5)  {"label":"startsWith","avg":3.55448}

Firefox 67 (indexOf勝利):

false results from fastest to slowest avg
1)  {"label":"indexOf","avg":0.1807}
2)  {"label":"startsWith","avg":0.74621}
3)  {"label":"substring","avg":0.74898}
4)  {"label":"slice","avg":0.78584}
5)  {"label":"lastIndexOf","avg":0.79668}

true results from fastest to slowest avg:
1)  {"label":"indexOf","avg":0.09528}
2)  {"label":"substring","avg":0.75468}
3)  {"label":"startsWith","avg":0.76717}
4)  {"label":"slice","avg":0.77222}
5)  {"label":"lastIndexOf","avg":0.80527}

Safari 12 (slice偽の結果でstartsWith勝ち、真の結果で勝ち、また、テスト全体を実行する合計時間の点で Safari が最速):

false results from fastest to slowest avg:
1) "{\"label\":\"slice\",\"avg\":0.0362}"
2) "{\"label\":\"startsWith\",\"avg\":0.1141}"
3) "{\"label\":\"lastIndexOf\",\"avg\":0.11512}"
4) "{\"label\":\"substring\",\"avg\":0.14751}"
5) "{\"label\":\"indexOf\",\"avg\":0.23109}"

true results from fastest to slowest avg:
1) "{\"label\":\"startsWith\",\"avg\":0.11207}"
2) "{\"label\":\"lastIndexOf\",\"avg\":0.12196}"
3) "{\"label\":\"substring\",\"avg\":0.12495}"
4) "{\"label\":\"indexOf\",\"avg\":0.33667}"
5) "{\"label\":\"slice\",\"avg\":0.49923}"

Opera 62 (substring勝利。結果は Chrome に似ています。Opera は Chromium と Blink に基づいているため、私は驚きません):

false results from fastest to slowest avg:
{"label":"substring","avg":0.09321}
{"label":"slice","avg":0.09463}
{"label":"lastIndexOf","avg":0.95347}
{"label":"indexOf","avg":1.6337}
{"label":"startsWith","avg":3.61454}

true results from fastest to slowest avg:
1)  {"label":"substring","avg":0.08855}
2)  {"label":"slice","avg":0.12227}
3)  {"label":"indexOf","avg":0.79914}
4)  {"label":"lastIndexOf","avg":1.05086}
5)  {"label":"startsWith","avg":3.70808}

すべてのブラウザーには独自の実装の詳細があることがわかります (Chrome の Chromium と Blink に基づく Opera は別として)。

もちろん、さまざまなユースケースでさらにテストを実行できますし、実行する必要があります (たとえば、干し草の山に比べて針が非常に短い場合、干し草の山が針よりも短い場合など...)、しかし私の場合は、非常に長い文字列とここで共有したかった。

于 2019-07-14T14:26:44.320 に答える
2

この文字列ライブラリについて学びました:

http://stringjs.com/

js ファイルをインクルードしてから、次のSように変数を使用します。

S('hi there').endsWith('hi there')

インストールすることで、NodeJS でも使用できます。

npm install string

S次に、それを変数として要求します。

var S = require('string');

Web ページには、別の文字列ライブラリへのリンクもあります (これが気に入らない場合)。

于 2014-04-29T10:22:18.047 に答える
1
var str = 'hol';
var data = 'hola mundo';
if (data.length >= str.length && data.substring(0, str.length) == str)
    return true;
else
    return false;
于 2012-05-04T14:04:52.403 に答える
0

ここでの回答に基づいて、これは私が現在使用しているバージョンです。これは、JSPerf テストに基づいて最高のパフォーマンスを提供するように思われるためです (そして、私が知る限り、機能的に完全です)。

if(typeof String.prototype.startsWith != 'function'){
    String.prototype.startsWith = function(str){
        if(str == null) return false;
        var i = str.length;
        if(this.length < i) return false;
        for(--i; (i >= 0) && (this[i] === str[i]); --i) continue;
        return i < 0;
    }
}

これは、http: //jsperf.com/startswith2/6の startsWith2 に基づいています。パフォーマンスを少し改善するために小さな調整を追加し、比較文字列が null または未定義であることのチェックも追加し、CMS の回答の手法を使用して String プロトタイプに追加するように変換しました。

この実装は、このMozilla Developer Networkページで言及されている「位置」パラメーターをサポートしていませんが、ECMAScript 提案の一部ではないようです。

于 2014-09-24T15:29:26.357 に答える
0

JavaScriptについてはわかりませんが、typescriptでは次のようなことをしました

var str = "something";
(<String>str).startsWith("some");

jsでも動作するはずです。それが役立つことを願っています!

于 2019-07-11T09:09:47.443 に答える
-2

startsWith()andを使用している場合はendsWith()、先頭のスペースに注意する必要があります。完全な例を次に示します。

var str1 = " Your String Value Here.!! "; // Starts & ends with spaces    
if (str1.startsWith("Your")) { }  // returns FALSE due to the leading spaces…
if (str1.endsWith("Here.!!")) { } // returns FALSE due to trailing spaces…

var str2 = str1.trim(); // Removes all spaces (and other white-space) from start and end of `str1`.
if (str2.startsWith("Your")) { }  // returns TRUE
if (str2.endsWith("Here.!!")) { } // returns TRUE
于 2012-10-21T06:07:57.867 に答える
-3

独自のプロトタイプ/配列プロトタイプへの拡張を作成することにより、文字列で始まる配列のすべてのメンバーを返すこともできます。別名

Array.prototype.mySearch = function (target) {
    if (typeof String.prototype.startsWith != 'function') {
        String.prototype.startsWith = function (str){
        return this.slice(0, str.length) == str;
      };
    }
    var retValues = [];
    for (var i = 0; i < this.length; i++) {
        if (this[i].startsWith(target)) { retValues.push(this[i]); }
    }
    return retValues;
};

そしてそれを使用するには:

var myArray = ['Hello', 'Helium', 'Hideout', 'Hamster'];
var myResult = myArray.mySearch('Hel');
// result -> Hello, Helium
于 2013-07-19T21:50:02.373 に答える