I was on code wars (fundamentals) and there was a kata that asked me to make a program that allows you to see if amount of 'x'
and 'o'
are the same (for example 'xXXooO'
should return true
and 'xXxxO'
should return false
).
Using my best knowledge about coding (which is a little) I built this code but it wouldn't work.
function XO(str) {
let string = str;
const o = string.match(/O/g) string.match(/o/g);
const x = string.match(/X/g) string.match(/x/g);
if (o.length != x.length) {
return true;
} else {
return false;
}
}
Please tell me what is wrong with my code.
This part is after I updated.
I updated my code but it says that null is not an object. I updated the variables too, and I don't think that is the reason why.
function XO(str) {
let string = str;
const largeO = string.match(/O/g);
const smallO = string.match(/o/g);
const largeX = string.match(/X/g);
const smallX = string.match(/x/g);
const oCombined = largeO.length smallO.length;
const xCombined = largeX.length smallX.length;
if (oCombined = xCombined) {
return true;
} else {
return false;
}
}
console.log(XO("OxX"));
CodePudding user response:
One needs to use an regex' i
modifier (or flag) for case insensitive matches of 'x'
/'X'
and 'o'
/'O'
.
And of cause one needs to handle the null
return value of a failing match
method which for the next provided example code is taken care of by Optional chaining / ?.
and the Nullish coalescing operator / ??
.
function isXAndOWithSameAmount(value) {
// always assure a string type
value = String(value);
// in case of a `null` value ... ...count is -1.
const xCount = value.match(/x/gi)?.length ?? -1;
// in case of a `null` value ... ...count is -2.
const oCount = value.match(/o/gi)?.length ?? -2;
// thus the return value for neither an 'x'/`X`
// match nor an 'o'/`O` match will always be `false`.
return (xCount === oCount);
// in order to achieve another (wanted/requested)
// behavior one needs to change both values after
// the nullish coalescing operator accordingly.
}
console.log(
"isXAndOWithSameAmount('xXXooO') ..?",
isXAndOWithSameAmount('xXXooO')
);
console.log(
"isXAndOWithSameAmount('xXoXooOx') ..?",
isXAndOWithSameAmount('xXoXooOx')
);
console.log(
"isXAndOWithSameAmount('xXxxO') ..?",
isXAndOWithSameAmount('xXxxO')
);
console.log(
"isXAndOWithSameAmount('xOoXxxO') ..?",
isXAndOWithSameAmount('xOoXxxO')
);
console.log(
"isXAndOWithSameAmount('') ..?",
isXAndOWithSameAmount('')
);
console.log(
"isXAndOWithSameAmount('bar') ..?",
isXAndOWithSameAmount('bar')
);
.as-console-wrapper { min-height: 100%!important; top: 0; }
One of cause can achieve the same behavior by casting the result of match
and an optionally chained ?.length
into an integer value via parseInt
which will return either an (integer) number value grater than zero or the NaN
value.
function isXAndOWithSameAmount(value) {
// always assure a string type
value = String(value);
// making use of optional chaining and `parseInt`
// which will result in (integer) number values
// grater than zero or the `NaN` value.
const xCount = parseInt(value.match(/x/gi)?.length);
const oCount = parseInt(value.match(/o/gi)?.length);
// since a `NaN` value is not equal to itself
// the return value for neither an 'x'/`X` match
// nor an 'o'/`O` match will always be `false`.
return (xCount === oCount);
}
console.log(
"isXAndOWithSameAmount('xXXooO') ..?",
isXAndOWithSameAmount('xXXooO')
);
console.log(
"isXAndOWithSameAmount('xXoXooOx') ..?",
isXAndOWithSameAmount('xXoXooOx')
);
console.log(
"isXAndOWithSameAmount('xXxxO') ..?",
isXAndOWithSameAmount('xXxxO')
);
console.log(
"isXAndOWithSameAmount('xOoXxxO') ..?",
isXAndOWithSameAmount('xOoXxxO')
);
console.log(
"isXAndOWithSameAmount('') ..?",
isXAndOWithSameAmount('')
);
console.log(
"isXAndOWithSameAmount('bar') ..?",
isXAndOWithSameAmount('bar')
);
.as-console-wrapper { min-height: 100%!important; top: 0; }