I think the issue is that whatever value I have it will always end up being true. If someone could help explain it to me with simple JavaScript for a beginner
function match(string, pattern) {
var i;
var letterFound = true;
var str = string.length;
if (string.indexOf(pattern) != -1)
{
letterFound = true;
} else letterFound = false;
return letterFound;
}
alert(match("abcdef", "#C2D!"));
alert(match("abcdef", "CAfe"));
alert(match("abcdef", "CG"));
Instead of looping through each character, you can use:
string.indexOf(pattern);
Which checks if string contains pattern in one go.
Delete all chars that are not letters with replace(/[^[A-Za-z]]/g, "")
Make array with String.prototype.split()
Go through the array with Array.prototype.map()
Check if every letter (case insensitive) is in the string with String.prototype.includes(). Return bools.
If every bool is true, return true, else return false. ( Array.prototype.every() )
function match(string, pattern) {
return pattern.replace(/[^A-Za-z]/g, "").split("").map(ch => {
return string.includes(ch.toLowerCase());
}).every(bool => bool === true) ? true : false;
}
console.log(match("abcdef", "#C2D!"));
console.log(match("abcdef", "CAfe"));
console.log(match("abcdef", "CG"));
Related
(JavaScript)
So, I need a function checkString(str, substr) that checks whether a string is made out of multiple occurences of a given substring.
Examples:
checkString("abc", "abc") -> true
checkString("abcabcabc", "abc") -> true
checkString("abcdef", "abc") -> false
checkString("abcab", "abc) -> true
Could someone help me out?
If whitespaces don't matter, this is a solution:
const checkString = (bigString, subString) => {
const split = bigString.split(subString);
const onlyOccurances = split.filter(v => v === '');
return split.length === onlyOccurances.length
}
checkString("abc", "abc") // true
checkString("abcabcabc", "abc") // true
checkString("abcdef", "abc") // false
bigString.split(subString) will split the big string into an array of empty strings if there's perfect match, and the length of it will be exactly how many occurances there are. If any of the values in the array are not empty strings, it means there is not a perfect match so there will be a difference between the length of the filtered by empty and the length of the splited values.
Hope it makes sense.
This method will return an object and found will be true if the value is found in the string and multipleFound will be true if found more than once;
const checkString = function(str, v) {
let found = false,
multi = false,
index;
index = str.indexOf(v);
if (index !== -1) {
found = true;
index = str.indexOf(v, index + v.length);
if (index !== -1) {
multi = true;
}
}
return {
found : found,
multipleFound : multi
};
};
This would be one way to check against the pattern abc:
const rx=/^(abc)+$/;
console.log(["abc","abcabcabc","abcdef"].map(t=>
`${t} ${rx.test(t)}`))
I'm trying to create a basic algorithm that checks if the string is ending with a provided parameter.
My problem is my code works only if the provided parameter is a single character.
Here is my code :
function confirmEnding(str, target) {
let arr = str.split('');
if(target === arr[arr.length-1]){
return true;
}else
return false;
}
confirmEnding("Sebastian", "n");
Use String.prototype.endsWith.
function confirmEnding(str, target) {
return str.endsWith(target);
}
Manually, slice the target's length off.
function confirmEnding(str, target) {
return str.slice(-1 * target.length) === target;
}
console.log(confirmEnding("Sebastian", "ian"));
I am attempting to solve this codewars problem:
Complete the function scramble(str1, str2) that returns true if a
portion of str1 characters can be rearranged to match str2, otherwise
returns false.
examples:
scramble('rkqodlw', 'world') ==> True
scramble('cedewaraaossoqqyt', 'codewars') ==> True
scramble('katas', 'steak') ==> False
This is my attempt:
function scramble(str1, str2) {
let obj1 = {};
let obj2 = {};
for (el of str1) {
obj1[el] = (obj1[el] || 0) + 1;
}
for (el of str2) {
obj2[el] = (obj2[el] || 0) + 1;
}
for (el in obj2) {
if (!(el in obj1)) return false;
}
return true;
}
I am converting the strings to objects, and then comparing the keys to each other. My code passes about 90% of all the tests on Codewars, but then it does not pass the other 10% and they do not show what the test inputs are unfortunately.
My hunch is that there are a few edge cases that this code is not catching. Any help would be appreciated.
You will need to handle the case when str2 has more instances of a letter than str1.
For example:
scramble("a", "aa")
Which should evaluate to false (not enough 'a's in "a" to form "aa").
You need to handle the amount of characters. Now you just checking whether the character in str2 also exists in str1.
So instead of:
for (el in obj2) {
if (!(el in obj1)) return false;
}
Try:
for (let [key, value] of Object.entries(obj2)) {
if (obj1[key] === undefined || obj1[key] < value) return false;
}
Which means that if obj1[key] doesn't exist or it has less occurrences than obj2[key] it will return false.
this code maybe helps
function scramble(str1, str2) {
let occurences = str1.split("").reduce((arr, cur) => { arr[cur] ? arr[cur]++ : arr[cur] = 1; return arr; }, {});
console.log(occurences);
return str2.split("").every((character) => --occurences[character] >= 0);
}
console.log(scramble("awpoirwled", "world"));
The algorithm I would use is to take each letter of the match string, and if its got an equivalent in the searched string, remove it from there and continue, otherwise abort if there is no match.
If you reach the end of the match string without aborting then you have a match
There is a list of strings and I want to check if the one I check has a value from there.
For example, the list is "good", "amazing", "bad", "better", "worse"
and this function:
checkPositive = (str) => {
if(str === "good" || str === "amazing" || str === "better") {
return true;
}
return false;
}
My question is if it's possible to do it more efficiently than it is now, I don't like how that if statement looks.
You could use an array and .includes:
checkPositive = str => ['good', 'amazing', 'better'].includes(str)
Build a dictionary:
let dict={
good: true
, amazing: true
, better: true
};
checkPositive = str => { return dict[str]; } // dict[str] ? true : false, if you need actual boolean values
You can use indexOf which will return -1 is the string is not present in list(assuming it is an array)
const strList = ["good", "amazing", "bad", "better", "worse"]
checkPositive = (str) => {
return strList.indexOf(str) !== -1 ? true : false;
}
console.log(checkPositive('good')) // true;
console.log(checkPositive('hello')) // true;
You could also use Regular_Expressions as well to check the particular string
const checkPositive = str => /good|amazing|better/.test(str.toLowerCase());
console.log(`For bad ` +checkPositive('bad'));
console.log(`For amazing `+checkPositive('amazing'));
I try to check if a word (wordToCheck) only consists of letters from an array (letters) and also contains every letter in the array only as often (or rather not more times than they are in the array) as it actually is inside of the array.
Here are examples of what the desired function should return:
checkIfWordContainsLetters("google", ["a","o","o","g","g","l","e","x"]) === true
checkIfWordContainsLetters("google", ["a","o","g","g","l","e","x"]) === false
How can I make this code work?
function checkIfWordContainsLetters(wordToCheck, letters) {
var lettersToString = letters.toString();
var lettersTrimmed = lettersToString.replace(/,/gi, "?");
var regEx = new RegExp(lettersTrimmed, "gi");
if (wordToCheck.match(regEx)!== null) {
return true;
}
else return false;
}
You could use this ES6 function:
function checkIfWordContainsLetters(wordToCheck, letters){
return !letters.reduce((a, b) => a.replace(b,''), wordToCheck.toLowerCase()).length;
}
console.log(checkIfWordContainsLetters("google", ["a","o","o","g","g","l","e","x"]));
console.log(checkIfWordContainsLetters("google", ["a","o","g","g","l","e","x"]));
The idea is to go through each letter in the letters array, and remove one (not more!) occurrence of it in the given wordToCheck argument (well, not exactly in it, but taking a copy that lacks that one character). If after making these removals there are still characters left over, the return value is false -- true otherwise.
Of course, if you use Internet Explorer, you won't have the necessary ES6 support. This is the ES5-compatible code:
function checkIfWordContainsLetters(wordToCheck, letters){
return !letters.reduce(function (a, b) {
return a.replace(b, '');
}, wordToCheck.toLowerCase()).length;
}
console.log(checkIfWordContainsLetters("google", ["a","o","o","g","g","l","e","x"]));
console.log(checkIfWordContainsLetters("google", ["a","o","g","g","l","e","x"]));
As long as it is not the best solution for long strings for which using some clever regex is definitely better, it works for short ones without whitespaces.
function checkIfWordContainsLetters(word, letters){
word = word.toLowerCase().split('');
for(var i = 0; i < letters.length; i++) {
var index = word.indexOf( letters[i].toLowerCase() );
if( index !== -1 ) {
// if word contains that letter, remove it
word.splice( index , 1 );
// if words length is 0, return true
if( !word.length ) return true;
}
}
return false;
}
checkIfWordContainsLetters("google", ["a","o","o","g","g","l","e","x"]); // returns true
checkIfWordContainsLetters("google", ["a","o","g","g","l","e","x"]); // returns false