This is project from freecodecamp where a string is encrypt by the values of the letters are shifted by 13 places
All letters will be uppercase. Do not transform any non-alphabetic character (i.e. spaces, punctuation), but do pass them on.
i test numadd by regex numadd is either equal to num+13 or numadd-26. some letter went wrong and do not return an uppercase letter
please someone explain whats wrong
function rot13(str) {
var str2 = '';
var arr1 = []
var arr2 = []
var reg = /[^A-Z]/
// var char
if (str.includes(' ') == false) {
for (let i = 0; i < str.length; i++) {
var char = '';
var numres
let num = str.charCodeAt(i)
// console.log(num)
// var numadd = num + 13;
// if num+13 not uppercase
if (reg.test(num + 13)) {
numres = num - 13
}
// if num+13 is uppercase
else {
numres = num + 13
}
char = String.fromCharCode(numres)
str2 += char
}
console.log(str2);
}
}
rot13("SERRPBQRPNZC");
reg.test(num + 13) checks the textual representation of the number num + 13 (applying implicit type conversion) so it always says True (do not match an uppercase letter) and always is computed numres = num - 13.
Use reg.test(String.fromCharCode(num + 13)) instead as follows:
function rot13(str) {
var str2 = '';
var arr1 = []
var arr2 = []
var reg = /[^A-Z]/
// var char
if (str.includes(' ') == false) {
for (let i = 0; i < str.length; i++) {
var char = '';
var numres
let num = str.charCodeAt(i)
// console.log(num)
// var numadd = num + 13;
// if num+13 not uppercase
// ↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓
if (reg.test(String.fromCharCode(num + 13))) {
numres = num - 13
}
// if num+13 is uppercase
else {
numres = num + 13
}
char = String.fromCharCode(numres)
str2 += char
}
console.log(str2);
}
}
rot13("SERRPBQRPNZC");
Related
filterString('str$$$1232text%<>');
The answer should be like
a = 'strtext'
b = '$$$%<>'enter code here
c = '1231'
Going by your question, assuming it to be in string, two possible ways are checking by regex or Unicode.
word = 'str$$$1232text%<>'
console.log(filterStringByUnicode(word))
console.log(filterStringByRegex(word))
function filterStringByRegex(word){
let str = num = spl = '';
[...word].forEach(el => {
if(el.match(/[a-z]/))
str += el;
else if(el.match(/[0-9]/))
num += el;
else
spl += el;
})
return {a:str,b:spl,c:num}
}
function filterStringByUnicode(word){
let str = num = spl = '';
[...word].forEach(el => {
let unicode = el.charCodeAt(0)
if(unicode >= 91 && unicode <= 122) //Unicode for a-z
str += el;
else if(unicode >= 48 && unicode <= 57) //Unicode for numbers
num += el;
else //rest
spl += el;
})
return {a:str,b:spl,c:num}
}
Your question seems not to be about filters but about how to split a string into substrings following some rules. I suggest you to look around RegExp(theRule) in JS.
A solution could be similar to :
var aString = 'str$$$1232text%<>';
var a=''; var b=''; var c='';
var regexA = new RegExp('[a-z]'); // lowercase a to z
var regexB = new RegExp('$%<>'); // only this special chars but you can add more
var regexC = new RegExp('[0-9]'); // 0 to 9
for(const aCharacter of aString.split('')){ // split will make an Array of chars
if (regexA.test(aCharacter) // the 'test' method return true if the char respect the regex rule
a = a.concat(aCharacter);
if (regexB.test(aCharacter)
b = b.concat(aCharacter);
if (regexC.test(aCharacter)
c = c.concat(aCharacter);
}
I am trying to make a Caesar's Cipher for a challenge, and there are specific rules I must follow:
The algorithm uses a numeric "shift" value. You should use a shift of 8 in your code.
You should IGNORE any characters that are not a letter (this includes symbols such as #*!$^) and they should not be in your output (however a space will remain a space in the encrypted string).
Your output should take into account both uppercase and lowercase letters. That is, both a lowercase 'a' and uppercase 'A' will have the same shift value.
Your final answer should be in all capital letters.
JS code:
function shift8(string){
string = string.toUpperCase();
const alphabetArray = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'.split('');
let shiftedString = '';
for (i = 0; i < string.length; i++) {
var currentIndex = alphabetArray.indexOf(string[i]);
var newIndex = currentIndex + 8;
var currentCharacter = alphabetArray[currentIndex];
var shiftedCharacter = alphabetArray[newIndex];
if (currentCharacter == ' ') {
shiftedString += ' ';
} else if ('ABCDEFGHIJKLMNOPQRSTUVWXYZ '.includes(shiftedCharacter)) {
shiftedString += shiftedCharacter;
}
}
return shiftedString;
}
var output = shift8('The quick brown fox jumps over the lazy dog');
console.log(output);
Is there something I am missing? Is my logic incorrect?
alphabetArray.indexOf(string[i]) will return -1 for all values not part of alphabetArray, such as spaces. This means that currentCharacter will be undefined for any such values.
To fix this, do var currentCharacter = string[i]; instead.
Your variable currentCharacter is just a member of alphabetArray, which doesn't contain any ' ' (spaces), that's why it's never triggered.
Here, I refactored your code. There is one important thing - you need to loop those indexes, as their max value should be of alphabetArray.length.
function shift8(string){
string = string.toUpperCase();
const alphabetArray = 'ABCDEFGHIJKLMNOPQRSTUVXYZABCDEFGHIJKLMNOPQRSTUVWXYZA'.split('');
let shiftedString = '';
for (i = 0; i < string.length; i++) {
let oldCharacter = string[i];
if( !alphabetArray.includes(oldCharacter) ){
if( oldCharacter == ' ' ) shiftedString += oldCharacter;
} else{
let currentIndex = alphabetArray.indexOf(oldCharacter);
let newIndex = (currentIndex + 8) % alphabetArray.length;
let shiftedCharacter = alphabetArray[newIndex];
shiftedString += shiftedCharacter;
}
}
return shiftedString;
}
var output = shift8('The quick brown fox jumps over the lazy dog');
console.log(output);
For an space the following will return -1
var currentIndex = alphabetArray.indexOf(string[i]);
If you should use a shift of 8 in your code alphabetArray doesn't need to have repeated values after the first eight characters in the alphabet because you will never use these values.
The code should be:
function shift8(string){
string = string.toUpperCase();
const alphabetArray = 'ABCDEFGHIJKLMNOPQRSTUVXYZABCDEFGH'.split('');
let shiftedString = '';
for (i = 0; i < string.length; i++) {
const element = string[i]
if (element == ' ') {
shiftedString += ' ';
} else {
const currentIndex = alphabetArray.indexOf(string[i]);
if(currentIndex === -1){ // To not include symbols such as #*!$^
continue
}
const newIndex = currentIndex + 8;
const currentCharacter = alphabetArray[currentIndex];
const shiftedCharacter = alphabetArray[newIndex];
shiftedString += shiftedCharacter
}
}
return shiftedString;
}
var output = shift8('The quick brown fox jumps over the lazy dog');
console.log(output); // CPM ZDQKS JAXHV NXF RDUYB XEMA CPM TIHG LXO
A lot of solutions I found here are giving true or false after checking if a string is a palindrome. I have a function that checks if a string is a palindrome or not:
function palindrome(myString){
/* remove special characters, spaces and make lowercase*/
var removeChar = myString.replace(/[^A-Z0-9]/ig, "").toLowerCase();
/* reverse removeChar for comparison*/
var checkPalindrome = removeChar.split('').reverse().join('');
/* Check to see if myString is a Palindrome*/
if(removeChar === checkPalindrome){
document.write("<div>"+ myString + " is a Palindrome <div>");
}else{
document.write("<div>" + myString + " is not a Palindrome </div>");
}
}
palindrome("Oh who was it I saw, oh who?")
palindrome("Madam")
palindrome("Star Wars")
But this is not quite what I want. It's just checking if the string is a palindrome or not. I want to update the function so that it identifies all of the palindromes in a sentence instead of giving it true or false. So if there's a sentence like this - "Madam and John went out at noon" It will list the palindromes in that sentence - "Madam, noon"
Any help in this would be appreciated!
function findPalindromes(str, min) {
min = min || 3;
var result = [];
var reg = str.toLowerCase();
var reg = reg.replace(/[^a-z]/g, ''); // remove if you want spaces
var rev = reg.split("").reverse().join("");
var l = reg.length;
for (var i = 0; i < l; i++) {
for (var j = i + min; j <= l; j++) {
var regs = reg.substring(i, j);
var revs = rev.substring(l - j, l - i);
if (regs == revs) {
result.push(regs);
}
}
}
return result;
}
var str1 = "Madam and John went out at noon";
console.log(str1, findPalindromes(str1));
var str2 = "\"Amore, Roma\" and \"There's no 'x' in Nixon\" are palindromes.";
console.log(str2, findPalindromes(str2));
function findPalindromes(sentence) {
const words = sentence.replace(/[^\w\s]/gi, '').split(' ');
const palindromes = words.filter(isPalindrome);
return palindromes;
}
function isPalindrome(word) {
if (word.length <= 0) return false;
word = word.toLowerCase();
for (let i = 0; i < word.length / 2; i++) {
if (word[i] !== word[word.length - 1 - i]) return false;
}
return true;
}
https://jsfiddle.net/ewezbz22/1/
Want to know if the substring of string is in the another string.
For eg..
var firstString= test123;
var secondString= nest145;
var thirdString= test456;
var fourString= teating456;
Result should be after comparing firstString and secondString
est1 is matched.
Result should be after comparing firstString and thirdString
test is matched.
Result should be after comparing firstString and fourString
No match found.
Limit to check the word-length can be decided.For the above example it is 4
Here is a simple sample, where the matched letters needs to be next after each other.
var firstString = 'test123';
var secondString = 'nest145';
var thirdString = 'test456';
var fourString = 'teating456';
function findMatchedChars(str1, str2, limit) {
var result = '', s1 = str1, s2 = str2;
if (str2.length > str1.length) {
s1 = str2;
s2 = str1;
}
for (var x = 0; x < s1.length; x++) {
if (s1[x] == s2[x]) {
result += s1[x];
} else {
if (result.length > 0 && result.length >= limit) return result;
result = '';
}
}
if (result.length > 0 && result.length >= limit) return result;
return 'No matches';
}
alert(findMatchedChars(firstString,secondString,4));
alert(findMatchedChars(firstString,thirdString,4));
alert(findMatchedChars(firstString,fourString,4));
This is LCS problem with tow string...
LCS
Here is the regex version:
var firstString = 'test123';
var secondString = 'nest145';
var thirdString = 'test456';
var fourString = 'teating456';
function findDups(str1, str2, limit) {
var re = '.*([^\\s]{' + limit + '}).*\\s+.*\\1.*'
var m = (str1 + " " + str2).match(re)
if (m != null) {
alert(m[1])
} else
alert('No matches')
}
findDups(firstString, secondString, 4)
findDups(firstString, thirdString, 4)
findDups(firstString, fourString, 4)
I have a variable which contains this:
var a = "hotelRoomNumber";
Is there a way I can create a new variable from this that contains: "Hotel Room Number" ? I need to do a split on the uppercase character but I've not seen this done anywhere before.
Well, you could use a regex, but it's simpler just to build a new string:
var a = "hotelRoomNumber";
var b = '';
if (a.length > 0) {
b += a[0].toUpperCase();
for (var i = 1; i != a.length; ++i) {
b += a[i] === a[i].toUpperCase() ? ' ' + a[i] : a[i];
}
}
// Now b === "Hotel Room Number"
var str = "mySampleString";
str = str.replace(/([A-Z])/g, ' $1').replace(/^./, function(str){ return str.toUpperCase(); });
http://jsfiddle.net/PrashantJ/zX8RL/1/
I have made a function here:
http://jsfiddle.net/wZf6Z/2/
function camelToSpaceSeperated(string)
{
var char, i, spaceSeperated = '';
// iterate through each char
for (i = 0; i < string.length; i++) {
char = string.charAt(i); // current char
if (i > 0 && char === char.toUpperCase()) { // if is uppercase
spaceSeperated += ' ' + char;
} else {
spaceSeperated += char;
}
}
// Make the first char uppercase
spaceSeperated = spaceSeperated.charAt(0).toUpperCase() + spaceSeperated.substr(1);
return spaceSeperated;
}
The general idea is to iterate through each char in the string, check if the current char is already uppercased, if so then prepend a space to it.