Check a string that MUST contain another string [duplicate] - javascript

This question already has answers here:
How to check whether a string contains a substring in JavaScript?
(3 answers)
Closed 9 years ago.
I want to check if string b is completely contained in string a.
I tried:
var a = "helloworld";
var b = "wold";
if(a.indexOf(b)) {
document.write('yes');
} else {
document.write('no');
}
The output is yes, it is not my expected output, because string b(wold) is not completely contained in string a(helloworld) --- wold v.s. world
Any suggestion to check the string?

Read the documentation: MDC String.indexOf :)
indexOf returns the index the match was found. This may be 0 (which means "found at the beginning of string") and 0 is a falsy value.
indexOf will return -1 if the needle was not found (and -1 is a truthy value). Thus the logic on the test needs to be adjusted to work using these return codes. String found (at beginning or elsewhere): index >= 0 or index > -1 or index != -1; String not found: index < 0 or index == -1.
Happy coding.

You need to use if(a.indexOf(b) > -1) instead. indexOf returns -1 when it can't find a string.

.indexOf returns -1 if no match was found, which is a truthy value. You'll need to check more explicitly:
if (a.indexOf(b) != -1)

That's because indexOf returns -1 if a value is not found:
if(a.indexOf(b) != -1) {

you may want to use this
if(a.indexOf(b) != -1)

You need to test if the result is -1. -1 indicates no match, but evaluates to true in a boolean sense.
var a = "helloworld";
var b = "wold";
if(a.indexOf(b) > -1) {
document.write('yes');
} else {
document.write('no');
}

Related

How do I check for two words on a string using include()?

I've tried &&, ||, and some other comparison methods between the words. Currently, it's like this:
if(str.includes("a", "b") {
console.log(a and b received)
}
And the problem is that currently, it logs that a and b received even if the string only has a, when I only want it to log that if the string has both a and b. Does anyone know what's the proper command for this? (ps I'm a total noob to js and I have no idea am I even supposed to use include() for something like this)
if(str.includes("a") && str.includes("b")) {
console.log(a and b received)
}
should do it.
There are various method:
Method 1 - using includes
str.includes("a") && str.includes("b")
Method 2 - using indexOf
str.indexOf("a") > -1 && str.indexOf("b") > -1
Method 3 - using contains
str.contains("a") && str.contains("b")
Method 4 - using search
str.search('a') > -1 && str.search('a') > -1
Method 5 - using match
str.match('a') && str.match('b')
Method 6 - using RegExp
RegExp('a').test(str) && RegExp('a').test(str)
if(str.includes('word1') && str.includes('word2')){
console.log("word1 and word2 received");
}
if(str.includes("a") && str.includes("b")) {
console.log("a and b received")
}
You can also read from the docs: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/includes, that includes function receives only a valueToFind argument (plus an optional fromIndex One), and that's the reason why your approach doesn't work.
A canonical solution is to take a quantifier, like Array#every and take the result.
The advantage is to have the option to add more values to the array for checking isntead of adding another condition for a check.
if (["a", "b"].every(part => str.includes(part)) {
console.log('str contains a and b');
}
As you can read on the docs the .includes() method determines whether one string may be found within another string, returning true or false as appropriate.
Can take up to 2 parameters the second parameter is optional (by default is 0) and indicates de position where is going to start the searching.
.includes() method is case sensitive so be aware of that.
let str = "Helloab World";
if ( str.includes("a") && str.includes("b") ){
console.log( "a and b received" )
} else {
console.log("String do not containt a or b")
}
// Example with the second parameter.
// Would go to the else statement because it would
// start searching from the 8th position of the string
console.log("Second if statement start here")
if ( str.includes("a", 8) && str.includes("b", 8) ){
console.log( "a and b received" )
} else {
console.log("String do not containt a or b")
}
Hope this example can help you a little.

Bean Counting WITHOUT using for loop and regex [duplicate]

This question already has answers here:
How to count string occurrence in string?
(40 answers)
Closed 2 years ago.
I tried to solve the following problem without using the for loop:
"Write a function countBs that takes a string as its only argument and returns a number that indicates how many uppercase “B” characters there are in the string.
console.log(countBs("BBC")); // → 2
Thank you for your help.
Here is the code I wrote so far which doesn't work:
function countBs(word) {
let count = 0
if (word.length == 0) {
return count;
} else {
if (word[word.length - 1] == 'B') {
count++
}
return countBs(word.slice(0, word.length - 1))
}
}
console.log(countBs("BBC"))
You can easily use regex for this case:
function countBs(word) {
const matches = word.match(/B/g);
return matches && matches.length || 0;
}
Basically it globally searches for occurrences of 'B'. If it find it, it returns the length of it, if the matches are null it will return 0.
Simpler less expressive:
function countBs(word) {
return (word.match(/B/g) || []).length;
}

indexOf is not working in JavaScript

I am checking an index Of string in JAVASCRIPT. and this is coming as false. where as the value does belong to it as below :
if(idOfControl.indexOf(idOfButton)) == is giving false for the below values.
idOfControl = "dlInventory_btnEditComment_0"
idOfButton = "dlInventory_btnEditComment"
But if I run idOfControl.replace(idOfButton, ""); It is working and replacing the text.
Any reason for this?
indexOf can also return 0, in the event of your string being found at the position 0. 0 evaluates to false. Try:
if(idOfControl.indexOf(idOfButton) > -1)
More info: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/indexOf
There are these three big options:
indexOf > -1
The result of indexOf can be 0 meaning that the string was found at the beginning of the string. When string is not found, the return value is -1, therefore:
if (idOfControl.indexOf(idOfButton) > -1) {
// Do something
}
Which can be nicer written as #paxdiablo commented:
if (idOfControl.indexOf(idOfButton) >= 0) {
// Do something
}
via regex
You can use a very simple regular expression to test your match.
var idOfControl = "dlInventory_btnEditComment_0"
var control = /dlInventory_btnEditComment/;
if (idOfControl.test(control)) {
// do something
}
This approach can be enhanced to capture the last number of your string (if you need it)
var idOfControl = "dlInventory_btnEditComment_0"
var control = /dlInventory_btnEditComment_(\d+)/;
var match = control.exec(idOfControl);
if (match) {
alert('the number found is: ' + match[1]);
}
You can try it out here: http://jsfiddle.net/4Z9UC/
via indexOf in a hacky way
This uses a bitwise operator to return a truthy value when the position is !=-1 (In two's complement notation, -1 is internally represented as 111...111, and its inversion is 000...000 which is 0, i.e. a falsy value). It is in fact more efficient than the >-1 option, but it is harder to read and to understand. (EDIT: this became so popular that you can say it is a standard)
if (~idOfControl.indexOf(idOfButton)) {
// do something
}

indexOf always returning true for document.location

I have the following script:
if (window.location.href.indexOf('env=P')) {
env = 'P';
console.log("P");
} else {
env = 'A';
console.log("A");
}
env is always equal to P no matter what the url is. I am quite sure I have used indexOf before for uri's but am not sure the issue here.
That's because indexOf doesn't return 0 and is therefore evaluated as true. Try changing to
if (window.location.href.indexOf('env=P') > -1)
indexOf will return -1 if the substring is not in the string, and -1 is a true value.
This is because it returns the index of the substring (so it is 'foo'.indexOf('f') that would return 0).
Your check should be:
if (location.href.indexOf('env=P') >= 0) {
indexOf returns -1 if there is no match, thats a Truthy value, you need to be explicit;
if (window.location.href.indexOf('env=P') === -1) {
///no match

endsWith in JavaScript

How can I check if a string ends with a particular character in JavaScript?
Example: I have a string
var str = "mystring#";
I want to know if that string is ending with #. How can I check it?
Is there a endsWith() method in JavaScript?
One solution I have is take the length of the string and get the last character and check it.
Is this the best way or there is any other way?
UPDATE (Nov 24th, 2015):
This answer is originally posted in the year 2010 (SIX years back.) so please take note of these insightful comments:
Shauna -
Update for Googlers - Looks like ECMA6 adds this function. The MDN article also shows a polyfill. https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String/endsWith
T.J. Crowder -
Creating substrings isn't expensive on modern browsers; it may well have been in 2010 when this answer was posted. These days, the simple this.substr(-suffix.length) === suffix approach is fastest on Chrome, the same on IE11 as indexOf, and only 4% slower (fergetaboutit territory) on Firefox: https://jsben.ch/OJzlM And faster across the board when the result is false: jsperf.com/endswith-stackoverflow-when-false Of course, with ES6 adding endsWith, the point is moot. :-)
ORIGINAL ANSWER:
I know this is a year old question... but I need this too and I need it to work cross-browser so... combining everyone's answer and comments and simplifying it a bit:
String.prototype.endsWith = function(suffix) {
return this.indexOf(suffix, this.length - suffix.length) !== -1;
};
Doesn't create a substring
Uses native indexOf function for fastest results
Skip unnecessary comparisons using the second parameter of indexOf to skip ahead
Works in Internet Explorer
NO Regex complications
Also, if you don't like stuffing things in native data structure's prototypes, here's a standalone version:
function endsWith(str, suffix) {
return str.indexOf(suffix, str.length - suffix.length) !== -1;
}
EDIT: As noted by #hamish in the comments, if you want to err on the safe side and check if an implementation has already been provided, you can just adds a typeof check like so:
if (typeof String.prototype.endsWith !== 'function') {
String.prototype.endsWith = function(suffix) {
return this.indexOf(suffix, this.length - suffix.length) !== -1;
};
}
/#$/.test(str)
will work on all browsers, doesn't require monkey patching String, and doesn't require scanning the entire string as lastIndexOf does when there is no match.
If you want to match a constant string that might contain regular expression special characters, such as '$', then you can use the following:
function makeSuffixRegExp(suffix, caseInsensitive) {
return new RegExp(
String(suffix).replace(/[$%()*+.?\[\\\]{|}]/g, "\\$&") + "$",
caseInsensitive ? "i" : "");
}
and then you can use it like this
makeSuffixRegExp("a[complicated]*suffix*").test(str)
Unfortunately not.
if( "mystring#".substr(-1) === "#" ) {}
Come on, this is the correct endsWith implementation:
String.prototype.endsWith = function (s) {
return this.length >= s.length && this.substr(this.length - s.length) == s;
}
using lastIndexOf just creates unnecessary CPU loops if there is no match.
This version avoids creating a substring, and doesn't use regular expressions (some regex answers here will work; others are broken):
String.prototype.endsWith = function(str)
{
var lastIndex = this.lastIndexOf(str);
return (lastIndex !== -1) && (lastIndex + str.length === this.length);
}
If performance is important to you, it would be worth testing whether lastIndexOf is actually faster than creating a substring or not. (It may well depend on the JS engine you're using...) It may well be faster in the matching case, and when the string is small - but when the string is huge it needs to look back through the whole thing even though we don't really care :(
For checking a single character, finding the length and then using charAt is probably the best way.
Didn't see apporach with slice method. So i'm just leave it here:
function endsWith(str, suffix) {
return str.slice(-suffix.length) === suffix
}
From developer.mozilla.org String.prototype.endsWith()
Summary
The endsWith() method determines whether a string ends with the characters of another string, returning true or false as appropriate.
Syntax
str.endsWith(searchString [, position]);
Parameters
searchString :
The characters to be searched for at the end of this string.
position :
Search within this string as if this string were only this long; defaults to this string's actual length, clamped within the range established by this string's length.
Description
This method lets you determine whether or not a string ends with another string.
Examples
var str = "To be, or not to be, that is the question.";
alert( str.endsWith("question.") ); // true
alert( str.endsWith("to be") ); // false
alert( str.endsWith("to be", 19) ); // true
Specifications
ECMAScript Language Specification 6th Edition (ECMA-262)
Browser compatibility
return this.lastIndexOf(str) + str.length == this.length;
does not work in the case where original string length is one less than search string length and the search string is not found:
lastIndexOf returns -1, then you add search string length and you are left with the original string's length.
A possible fix is
return this.length >= str.length && this.lastIndexOf(str) + str.length == this.length
if( ("mystring#").substr(-1,1) == '#' )
-- Or --
if( ("mystring#").match(/#$/) )
Just another quick alternative that worked like a charm for me, using regex:
// Would be equivalent to:
// "Hello World!".endsWith("World!")
"Hello World!".match("World!$") != null
String.prototype.endsWith = function(str)
{return (this.match(str+"$")==str)}
String.prototype.startsWith = function(str)
{return (this.match("^"+str)==str)}
I hope this helps
var myStr = “ Earth is a beautiful planet ”;
var myStr2 = myStr.trim();
//==“Earth is a beautiful planet”;
if (myStr2.startsWith(“Earth”)) // returns TRUE
if (myStr2.endsWith(“planet”)) // returns TRUE
if (myStr.startsWith(“Earth”))
// returns FALSE due to the leading spaces…
if (myStr.endsWith(“planet”))
// returns FALSE due to trailing spaces…
the traditional way
function strStartsWith(str, prefix) {
return str.indexOf(prefix) === 0;
}
function strEndsWith(str, suffix) {
return str.match(suffix+"$")==suffix;
}
I don't know about you, but:
var s = "mystring#";
s.length >= 1 && s[s.length - 1] == '#'; // will do the thing!
Why regular expressions? Why messing with the prototype? substr? c'mon...
I just learned about this string library:
http://stringjs.com/
Include the js file and then use the S variable like this:
S('hi there').endsWith('hi there')
It can also be used in NodeJS by installing it:
npm install string
Then requiring it as the S variable:
var S = require('string');
The web page also has links to alternate string libraries, if this one doesn't take your fancy.
If you're using lodash:
_.endsWith('abc', 'c'); // true
If not using lodash, you can borrow from its source.
function strEndsWith(str,suffix) {
var reguex= new RegExp(suffix+'$');
if (str.match(reguex)!=null)
return true;
return false;
}
So many things for such a small problem, just use this Regular Expression
var str = "mystring#";
var regex = /^.*#$/
if (regex.test(str)){
//if it has a trailing '#'
}
Its been many years for this question. Let me add an important update for the users who wants to use the most voted chakrit's answer.
'endsWith' functions is already added to JavaScript as part of ECMAScript 6 (experimental technology)
Refer it here: https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/String/endsWith
Hence it is highly recommended to add check for the existence of native implementation as mentioned in the answer.
function check(str)
{
var lastIndex = str.lastIndexOf('/');
return (lastIndex != -1) && (lastIndex == (str.length - 1));
}
A way to future proof and/or prevent overwriting of existing prototype would be test check to see if it has already been added to the String prototype. Here's my take on the non-regex highly rated version.
if (typeof String.endsWith !== 'function') {
String.prototype.endsWith = function (suffix) {
return this.indexOf(suffix, this.length - suffix.length) !== -1;
};
}
#chakrit's accepted answer is a solid way to do it yourself. If, however, you're looking for a packaged solution, I recommend taking a look at underscore.string, as #mlunoe pointed out. Using underscore.string, the code would be:
function endsWithHash(str) {
return _.str.endsWith(str, '#');
}
After all those long tally of answers, i found this piece of code simple and easy to understand!
function end(str, target) {
return str.substr(-target.length) == target;
}
if you dont want to use lasIndexOf or substr then why not just look at the string in its natural state (ie. an array)
String.prototype.endsWith = function(suffix) {
if (this[this.length - 1] == suffix) return true;
return false;
}
or as a standalone function
function strEndsWith(str,suffix) {
if (str[str.length - 1] == suffix) return true;
return false;
}
String.prototype.endWith = function (a) {
var isExp = a.constructor.name === "RegExp",
val = this;
if (isExp === false) {
a = escape(a);
val = escape(val);
} else
a = a.toString().replace(/(^\/)|(\/$)/g, "");
return eval("/" + a + "$/.test(val)");
}
// example
var str = "Hello";
alert(str.endWith("lo"));
alert(str.endWith(/l(o|a)/));
This builds on #charkit's accepted answer allowing either an Array of strings, or string to passed in as an argument.
if (typeof String.prototype.endsWith === 'undefined') {
String.prototype.endsWith = function(suffix) {
if (typeof suffix === 'String') {
return this.indexOf(suffix, this.length - suffix.length) !== -1;
}else if(suffix instanceof Array){
return _.find(suffix, function(value){
console.log(value, (this.indexOf(value, this.length - value.length) !== -1));
return this.indexOf(value, this.length - value.length) !== -1;
}, this);
}
};
}
This requires underscorejs - but can probably be adjusted to remove the underscore dependency.
if(typeof String.prototype.endsWith !== "function") {
/**
* String.prototype.endsWith
* Check if given string locate at the end of current string
* #param {string} substring substring to locate in the current string.
* #param {number=} position end the endsWith check at that position
* #return {boolean}
*
* #edition ECMA-262 6th Edition, 15.5.4.23
*/
String.prototype.endsWith = function(substring, position) {
substring = String(substring);
var subLen = substring.length | 0;
if( !subLen )return true;//Empty string
var strLen = this.length;
if( position === void 0 )position = strLen;
else position = position | 0;
if( position < 1 )return false;
var fromIndex = (strLen < position ? strLen : position) - subLen;
return (fromIndex >= 0 || subLen === -fromIndex)
&& (
position === 0
// if position not at the and of the string, we can optimise search substring
// by checking first symbol of substring exists in search position in current string
|| this.charCodeAt(fromIndex) === substring.charCodeAt(0)//fast false
)
&& this.indexOf(substring, fromIndex) === fromIndex
;
};
}
Benefits:
This version is not just re-using indexOf.
Greatest performance on long strings. Here is a speed test http://jsperf.com/starts-ends-with/4
Fully compatible with ecmascript specification. It passes the tests
Do not use regular expressions. They are slow even in fast languages. Just write a function that checks the end of a string. This library has nice examples: groundjs/util.js.
Be careful adding a function to String.prototype. This code has nice examples of how to do it: groundjs/prototype.js
In general, this is a nice language-level library: groundjs
You can also take a look at lodash
all of them are very useful examples. Adding String.prototype.endsWith = function(str) will help us to simply call the method to check if our string ends with it or not, well regexp will also do it.
I found a better solution than mine. Thanks every one.
For coffeescript
String::endsWith = (suffix) ->
-1 != #indexOf suffix, #length - suffix.length
This is the implementation of endsWith:
String.prototype.endsWith = function (str) {
return (this.length >= str.length) && (this.substr(this.length - str.length) === str);
}
7 years old post, but I was not able to understand top few posts, because they are complex. So, I wrote my own solution:
function strEndsWith(str, endwith)
{
var lastIndex = url.lastIndexOf(endsWith);
var result = false;
if (lastIndex > 0 && (lastIndex + "registerc".length) == url.length)
{
result = true;
}
return result;
}

Categories

Resources