The Problem:
Create a program that prompts for a list of numbers, separated by spaces. Have the program print out a new list containing only the even number.
Convert the input to (a array). Many languages can easily convert strings to arrays with a built in function that splits apart a string based on a specified delimiter.
Write your own algorithm- don't rely on the language's built-in filter or similar enumeration feature.
Use a function called "filterEvenNumbers" to encapsulate the logic for this. The function takes in the old array and returns the new array.
All my notes on this:
//global array
var arr = [];
var arr = prompt("Enter your numbers");
// var eachNumber = arr.split(",");
var res = arr.split("");
console.log(arr);
console.log(res);
if(res = )
// var str = "How are you doing today?";
//push elements into array
// arr.push(prompt("Enter in a bunch of numbers", "")); //push input to array
// console.log(arr);
// https://stackoverflow.com/questions/28252888/javascript-how-to-save-prompt-input-into-array
// var arr = prompt("Enter your numbers").split(",");
// console.log(arr);
// var arr = [];
// for(var i = 0; i < 10; i++)
// arr.push(prompt("Enter a number");
// Convert number into array in Javascript
// https://stackoverflow.com/questions/20730360/convert-number-into-array-in-javascript
// var numbers = "1, 2, 3";
// var eachNumber = numbers.split(",");
// /* now parse them or whatso ever */
// console.log(eachNumber);
// JavaScript Array filter
// http://www.diveintojavascript.com/core-javascript-reference/the-array-object/array-filter
// The JavaScript Array filter method iterates over each value of an array passing it to a callback function.
// If the callback function returns true, the current value is then pushed into the resulting array.
// The callback function is invoked with three arguments: the value of the element, the index of...
// the element and the Array object being traversed.
// Bellow is an example of filtering odd and even numbers out of an array:
// var arr = [1, 2, 3, 4, 5];
// var odd = arr.filter(function(val) {
// return 0 != val % 2;
// });
// // odd = [1, 3, 5]
// var even = arr.filter(function(val) {
// return 0 == val % 2;
// });
// even = [2, 4]
// console.log(even);
// The Array filter method can also be used to remove empty, null or undefined elements from an array:
// var arr = [0, null, 42, undefined, "", true, false, NaN, "", "foo bar"];
// var filteredArr = arr.filter(function(val, num) {
// return !(val === "" || typeof val == "undefined" || val === null );
// });
// // // filteredArr = [0, 42, true, false, NaN, "foo bar"]
// console.log(filteredArr);
var a = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
b = [];
for (var i = 0; i < a.length; ++i) {
if ((a[i] % 2) === 0) {
b.push(a[i]);
}
}
This is an example of an array that finds and pushes the even numbers into another array. You can easily change it, and it wont push it to the another array, but instead will print even numbers. It will help you solve your problem
Is there a part of the question you do not understand? What are you having trouble with?
In order to prompt for user input you can use window.prompt('Enter a list of numbers separated by spaces');
This way of receiving user input will return a string. Since you are not allowed to use built-in methods for turning this into a list, one approach you can take is :
Store the user input into a variable
Iterate through each character in the string. Have a variable currentInteger defined that holds the digits of the current number you are looking at in your string (remember: numbers can be longer than a single digit, so when iterating through the string your current number may not be represented by the single character you are looking at)
once you reach a space, you know that the currentInteger has been completed, append that to a new list IF it is an even integer.
Since your currentInteger variable is a string, you will need to use parseInt() to make it a number and check if it is even.
Related
My current goal is to take items in array integers and create a key pair value based on how many times the key appeared in integers. My logic is: for i in integers, if i is in integers 2 already, increment that key's value by 1. if it doesn't exist, create the key and pair it with a value of 1. It's been a few hours now and after heavy googling I can't seem to find where im messing my logic up.
//require realdine-sync module
var readlineSync = require('readline-sync');
//initialize variable and list
var integer;
integers2 = {};
var integers = [];
//user input
integer = readlineSync.question('Integer?: ')
//check user input and append any integer besides 0
while (integer != 0 && integer >= 1 && integer <= 100){
console.log("not 0!")
integers.push(integer)
integer = readlineSync.question('Integer?: ')
}
console.log(integers);
for(i in integers){if (i in integers2){integers2[i] += 1}else{integers2[i] = 1}
}
console.log(integers2)
let integers2 = {}
integers = [5, 4, 5, 2, 4, 7, 5];
// you were using 'in' instead 'of', 'in': gives you index , 'of'?: gives you value of array
for (let i of integers) {
if (integers2[i]) { // if key exist increment value by one
integers2[i] += 1
} else { // else add 1 as the first value
integers2[i] = 1
}
}
console.log(integers2);
This is a solution that you can try which works. It uses the same logic as you described in the question. This solution uses Array.prototype.reduce() with a Map().
const howMany = arr => arr
.reduce(
(map, n) => map.set(n, (map.get(n) ?? 0) + 1),
new Map()
)
console.log([...howMany([3, 4, 6, 4, 5, 5, 5])])
I am trying to improve in my Problem Solving Skills and would love to get some explanation on what it is that I am doing wrong or if I can get a hand in the right direction. My code below is what I am stuck on.
My problem, I am trying to check within the array if it contains any numbers that will sum up to a total given value. Pretty simple but a bit complex for a beginner.
My first Step is to setup a function with two parameters that accept the array and total amount we want.
const array = [10, 15, 7, 3];
function sumUpTotal(array, total) {
}
Then I want to iterate through my array to check each value within the array by using the forEach method to output each value
const array = [10, 15, 7, 3];
function sumUpTotal(array, total) {
array.forEach(value => value)
}
Now that I have all the outputs, I am stuck on how I can check if the numbers add up with each other to give out the total we want. Can someone please help.
The Output should be two numbers that add up to the total.
For example, given [10, 15, 3, 7] and k of 17, return true since 10 + 7 is 17.
Using forEach() to iterate over each value in the array and includes() to check if any values further ahead in the array sum to your total you can generate an array of unique sum pairs. By only looking forward from the given iteration one avoids generating duplicate pairings. (eg. avoids [[10, 7], [7, 10]] for you example input)
forEach() provides both the value and the index of the current iteration, which makes it simple to use the optional, second fromIndex argument of includes() to only look ahead in the array by passing index+1. If a match is found an array of [value, difference] is pushed to the result array. The return value is an array of sum pairs, or an empty array if there are no matches.
const array = [10, -2, 15, 7, 3, 2, 19];
function sumUpTotal(array, total) {
let result = []
array.forEach((value, index) => {
let diff = total - value;
if (array.includes(diff, index + 1)) result.push([value, diff]);
});
return result;
}
console.log(JSON.stringify(sumUpTotal(array, 17)));
.as-console-wrapper { max-height: 100% !important; top: 0; }
You can do this using a Set as follows:
function sumUpTotal(array, total) {
// initialize set
const set = new Set();
// iterate over array
for(let i = 0; i < array.length; i++){
// get element at current index
const num = array[i];
// get the remaining number from total
const remaining = total - num;
// if the remaining is already stored in the set, return numbers
if(set.has(remaining)) return [num, remaining];
// else add number to set
else set.add(num);
}
// return null if no two numbers in array that sum up to total
return null;
}
const array = [10, 15, 7, 3];
const total = 17;
console.log( sumUpTotal(array, total) );
I am having trouble with a problem and how to address it. Mind you, I am relatively new to JavaScript and the problem feels like I am over complicating it.
The problem:
Given a sequence of integers as an array, determine whether it is possible to obtain a strictly increasing sequence by removing no more than one element from the array.
Example
For sequence = [1, 3, 2, 1], the output should be
almostIncreasingSequence(sequence) = false;
There is no one element in this array that can be removed in order to get a strictly increasing sequence.
For sequence = [1, 3, 2], the output should be
almostIncreasingSequence(sequence) = true.
You can remove 3 from the array to get the strictly increasing sequence [1, 2]. Alternately, you can remove 2 to get the strictly increasing sequence [1, 3].
Thanks for all your comments! I wanted to update this to be a better question, and also inform you I have found a solution if someone would like to check it and see if there is a cleaner way to put it. :)
function almostIncreasingSequence(sequence) {
if(sequence.length == 2) return true;
var error = 0;
for(var i = 0; i < sequence.length - 1; i++){
if(sequence[i] >= sequence[i+1]){
var noStepBack = sequence[i-1] && sequence[i-1] >= sequence[i+1];
var noStepFoward = sequence[i+2] && sequence[i] >= sequence[i+2];
if(i > 0 && noStepBack && noStepFoward) {
error+=2;
}else{
error++;
}
}
if(error > 1){
return false;
}
}
return true;
}
Think about what your code:
sequence[i+1] - sequence[i] !== 1, variable++;
would do for the following array:[1,2,3,8,8].
From the problem description, it is not clear weather the program must remove one character. But if that is the case, the code below should do it.
function canGetStrictlyIncreasingSeq(numbers) {
var counter = 0;
var lastGreatestNumber = numbers[0];
for (var i = 1; i < numbers.length; i++) {
if (lastGreatestNumber >= numbers[i]) {
counter++;
lastGreatestNumber = numbers[i];
} else {
lastGreatestNumber = numbers[i];
}
}
if (counter <= 1)
return true;
return false;
}
var nums1 = [1, 2, 3, 4, 5]; //true
var nums2 = [1, 2, 2, 3, 4]; //true
var nums3 = [1, 3, 8, 1, 9]; //true
var nums4 = [3, 2, 5, 6, 9]; //true
var nums5 = [3, 2, 1, 0, 5]; //false
var nums6 = [1, 2, 2, 2, 3]; //false
var nums7 = [1, 1, 1, 1, 1]; //false
var nums8 = [1, 2]; //true
var nums9 = [1, 2, 2]; //true
var nums10 = [1, 1, 2, 3, 4, 5, 5]; //false
var nums11 = [10, 1, 2, 3, 4, 5]; //true
var nums12 = [1, 2, 3, 4, 99, 5, 6]; //true
console.log(canGetStrictlyIncreasingSeq(nums1));
console.log(canGetStrictlyIncreasingSeq(nums2));
console.log(canGetStrictlyIncreasingSeq(nums3));
console.log(canGetStrictlyIncreasingSeq(nums4));
console.log(canGetStrictlyIncreasingSeq(nums5));
console.log(canGetStrictlyIncreasingSeq(nums6));
console.log(canGetStrictlyIncreasingSeq(nums7));
console.log(canGetStrictlyIncreasingSeq(nums8));
console.log(canGetStrictlyIncreasingSeq(nums9));
console.log(canGetStrictlyIncreasingSeq(nums10));
console.log(canGetStrictlyIncreasingSeq(nums11));
console.log(canGetStrictlyIncreasingSeq(nums12));
Lets take a step back and think about the problem: "Given a sequence of Integers as an array" - we're dealing with arrays of data...but you already knew that.
"determine whether it is possible to obtain a strictly increasing sequence" ok, we need to make something that checks for valid sequence.
"by removing no more than one element from the array." so we can try plucking each element one-by-one and if at least one resulting array is sequential, its possible.
Now instead of one large problem we have two smaller ones
First, we're dealing with arrays, so avail yourself to JavaScript's built-in Array functions to make things easier. In the below, we use 'every()', 'forEach()', 'splice()', 'push()', and 'some()' You can read into how they work here https://www.w3schools.com/jsref/jsref_obj_array.asp It's not long and well worth your time.
Lets deal with the first problem: Determining if an array is sequential. The below function does this
function checkSequence(inputArray){
return inputArray.every(function(value, index, arr){
if (index == 0 && value < arr[index + 1]) {return true}
else if (index < arr.length && value < arr[index + 1] && value > arr[index - 1]) {return true}
else if (index = arr.length - 1 && value > arr[index - 1]) {return true}
else {return false}
});
}
It takes an input array, and uses an Array built-in function called every(), which runs a test on each element in an array
and returns 'true' if all the elements test true. Our test expects the first element to always be lower less than the second
for any given element to be greater than the previous, and less than the next, and for the last element to be greater than the next-to-last
if any element does not satisfy this test, the whole thing returns false
Now we have a means of seeing of an array is sequential, which will make the next part much easier
Now we make another function to pluck out individual elements and see if anythign works
function isPossible(input){
var results = []; //we will store our future results here
input.forEach(function(value, index, arr){
copy = Array.from(arr); //we work on a copy of 'arr' to avoid messing it up (splice mangles what you give it, and we need the un-maimed version for later iterations)
copy.splice(index, 1); //remove an element from copy (a copy of 'arr')
results.push(checkSequence(copy)); //see if it is still in sequence
});
return results.some(function(value){return value});
}
We first make an array to store the results of each attempt into the array 'results' we will use it later.
Then, we take a supplied array 'input' and use "forEach()", which performs a function with each element in an array.
for each element, we make a new array with that element removed from it, and we run the "checkSequence()"
function we made before on it, and finally store the result in the results array.
When the forEach is done, we take the results array and use 'some()' on it, which works just like 'every()'
only it returns true if at least one value is true
Now, you simply call isPossible(your_array) and it will satisfy the problem
Taking into account Patrick Barr's suggestion and assuming that es6 and arrow functions are fine, this solution using Array.prototype.filter could work. The filter itself will return array of elements that should be removed to satisfy conditions of the problem:
UPDATED
function isSequential(array) {
return array && array.length > 0 ? array.filter((x,i) => x >= array[i + 1] || array[i + 1] <= array[i - 1]).length < 2 : false;
}
console.log(isSequential([1]));
console.log(isSequential([1,2,4,5,6]));
console.log(isSequential([1,2,2,3,4,5,6]));
console.log(isSequential([1,4,3,2,5,6]));
console.log(isSequential([1,2,3,4,5,6]));
console.log(isSequential([1,2,0,3,4]));
console.log(isSequential([1,1]));
console.log(isSequential([1,2,0,1,2]));
console.log(isSequential([1,2,3,1,2,3]));
console.log(isSequential([]));
console.log(isSequential([1,0,0,1]));
console.log(isSequential([1,2,6,3,4])); //should be true, but return false
I was trying to solve some of the programming challenges at "free code camp" website, The problem was to find the symmetric difference between multiple arrays and returning an array of the symmetric difference of the provided arrays.
for example the following arrays:
[1, 2, 5], [2, 3, 5], [3, 4, 5]
should return [ 1, 4, 5 ]
so that's what I came up with:
function sym() {
var final = [];
var current_array = [];
for (var i = 0; i < arguments.length; i++) {
current_array = arguments[i];
//ensures duplicates inside each array are removed first
current_array = current_array.filter(function (element, index) {
return current_array.indexOf(element) == index;
});
for (var j = 0, end = current_array.length; j < end; j++) {
if(final.indexOf(current_array[j]) < 0)
final.push(current_array[j]);
else
// for some reason "splice" isn't working properly..
// final.splice(final.indexOf(current_array[j], 1));
delete final[final.indexOf(current_array[j])];
}
}
var final_2 = [];
// Removing the empty slots caused by the "delete" keyword usage
for (var m = 0; m < final.length; m++) {
if(typeof final[m] !== 'undefined')
final_2.push(final[m]);
}
return final_2;
}
in the previous logic I created an array called final that is supposed to hold all of the elements that only exist once in all of the passed arrays, firstly I loop over the arguments parameter which represents here the arrays and for each array I loop over its elements and check if that element exists in the final array or not. If it exists I remove it from the final array, else I push it to the array.
The problem here is if I use the splice method as given in the code above, it behaves very strangely, for example for the following arrays
[1, 2, 3], [5, 2, 1, 4], the result should be: [3, 5, 4]
when I use this line
final.splice(final.indexOf(current_array[j], 1));
instead of
delete final[final.indexOf(current_array[j])];
and return the final array it returns this [ 4 ]
here is the array values at each iteration
round (0, 0): 1
round (0, 1): 1,2
round (0, 2): 1,2,3
round (1, 0): 1,2,3,5
round (1, 1): 1
round (1, 2):
round (1, 3): 4
once it gets to an element that exists in the array it removes all of the elements starting from this element until the end of the array.
I don't know exactly if I'm missing something, I tried to search for any similar problems but most of what I came up with was a problem of removing elements from an array that the person was looping over and hence missing with its indices .. In my case the array I'm trying to modify got nothing to do with the arrays I'm iterating through.
Also I believe splice modifies the array in place and returns the removed elements.. please correct me if I'm not getting it well.
You've misplaced a ), here's the correction:
final.splice( final.indexOf(current_array[j]), 1 );
An additional note: the algorithm adds 5 for the first array, removes it for the second, and adds it again for the third (since it isn't present in final anymore), resulting in [1,4,5].
With an odd number of arguments, the value is preserved, with an even number, it is removed.
A simpler way to get all unique values from all arrays (if that is the intent), is to count the occurrences and filter on a single occurrence:
function sym2() {
var count = {};
for ( var i in arguments ) {
console.log("Processing ", i );
for ( var k = 0; k < arguments[i].length; k ++)
count[ arguments[i][k] ] = (count[ arguments[i][k] ]||0) + 1;
}
var final = [];
for ( var i in count )
if ( count[i] == 1 )
final.push( i );
return final;
}
sym2([1, 2, 5], [2, 3, 5], [3, 4, 5]);
Note that this will return [1,4] rather than [1,4,5].
Hi I'm struggling to solve this problem. How to create a javascript function that takes any number of arrays as arguments, then returns an array of elements that only appear in one of the arrays. All items that appear in multiple arrays are removed. Getting nowhere with a solution, suspect I'm not approaching it in the right way, stumped!
Edit: the other question addresses eliminating duplicate values in one array, I need to compare x number of separate arrays and return the values that aren't duplicated between arrays. So ([5,6,7],[5,8,9]) returns [6,7,8,9].
function sym(args) {
var ans = [];
for(var i =0;i<arguments.length;i++){
var tempArr = arguments[i].filter(function(el){
var filtTrue = false;
for(var j = 0;j<arguments.length;j++){
if(Array.isArray(arguments[j]) && arguments[j] !== arguments[i]){
if(arguments[j].indexOf(el) === -1){
filtTrue = true;
}}
}
return filtTrue;
});
ans = ans.concat(tempArr);
}
return ans;
}
Here's one way to do it. The idea here is that you create a map for keeping counts of all the items in the array. You then cycle through each array, look up each value in the map and, if found, you increment its count. If not found, you set the count to 1. Then, when done with all the arrays, you collect any items that have a count of 1.
You weren't specific about what to do if an item appears more than once in the same array, but not in any other array. This first solution will not include that item (since it detects duplicates). It could be adapted (with a little more complexity) to allow that item if that was an issue (see 2nd code block below for that implementation).
function sym(/* pass one or more arrays here */) {
var ans = [], cnts = {};
//count all items in the array
for (var i = 0; i < arguments.length; i++){
arguments[i].forEach(function(item) {
if (cnts.hasOwnProperty(item)) {
// increase cnt
++cnts[item].cnt;
} else {
// initalize cnt and value
cnts[item] = {cnt: 1, val: item};
}
});
}
for (var item in cnts) {
if (cnts.hasOwnProperty(item) && cnts[item].cnt === 1) {
ans.push(cnts[item].val);
}
}
return ans;
}
If you want to include items that are present more than once in a single array, but not present in any other array, then you can use this slightly more complicated adaptation:
function sym(/* pass one or more arrays here */) {
var ans = [], cnts = {}, currentMap;
//count all items in the array
for (var i = 0; i < arguments.length; i++){
currentMap = {};
arguments[i].forEach(function(item) {
// if we haven't already counted this item in this array
if (!currentMap.hasOwnProperty(item)) {
if (cnts.hasOwnProperty(item)) {
// increase cnt
++cnts[item].cnt;
} else {
// initalize cnt and value
cnts[item] = {cnt: 1, val: item};
}
}
// keep track of whethere we've already counted this item in this array
currentMap[item] = true;
});
}
// output all items that have a cnt of 1
for (var item in cnts) {
if (cnts.hasOwnProperty(item) && cnts[item].cnt === 1) {
ans.push(cnts[item].val);
}
}
return ans;
}
Working demo: http://jsfiddle.net/jfriend00/bete5k3n/
I know this is increadibly late but this is another way to do it. Maybe not the most rigorous one but certainly creative. The method Array.symmetricDifference() expects any number of arguments and returns the symmetric difference of those arguments.
Array.prototype.symmetricDifference = function() {
var args = [];
// copy arguments into a real array and get rid of duplicates with filter
for(var i = 0; i < arguments.length; i++) {
args[i] = arguments[i];
args[i] = args[i].filter(function(item, pos, self) {
return self.indexOf(item) == pos;
});
}
var diff = args[0];
// iterate through every arguments in args.
// concatenate the first two arguments to form a new set.
// now every number in this new set that was contained in both arguments
// from before will be contained at least twice in this new set.
for(var j = 1; j < args.length; j++) {
//sort the new set so that duplicates are next to each other.
diff = diff.concat(args[j]).sort();
var index = 0;
// now iterate through the new set and delete both duplicates if you
// find any. Otherwise proceed to the next index.
while(index < diff.length) {
// if duplicate is found delete both, otherwise look at next index.
diff[index] === diff[index + 1] ? diff.splice(index, 2) : index++;
}
}
return diff;
};
You can invoke that method on any array or create a new one and invoke it on that one like this for example:
// take any number of arrays
var a = [3, 3, 3, 2, 5];
var b = [2, 1, 5, 7];
var c = [3, 4, 6, 6];
var d = [1, 2, 3];
var e = [5, 3, 9, 8];
var f = [1];
// invoke the method on "solution" with any number of arguments
// and store it in solution.
var solution = solution.symmetricDifference(a,b,c,d,e,f);
console.log(solution); // [1, 2, 4, 5, 6, 7, 8, 9]
I hope this helps!
Finding unique items in multiple arrays
function uniqueItemsInArrays(...args){
let allItems = [];
allItems = allItems.concat(...args)
return allItems.filter(function(item, pos, self) {
return self.indexOf(item) === pos && self.indexOf(item,pos+1) === -1;
});
}
uniqueItemsInArrays( [1, 5, 1, 8, 1, 2],
[2, 2, 9, 3, 5],
[1, 4, 7, 6] );
The above code uses ES6 rest parameters to access all the arrays passed as arguments. Then using the concat() function, I am joining all the individual arrays to a single array. Finally, filter function has been used to identify and return the unique items from this array. The logic here is to find out the first index of the current item and if there are no more occurrence from the first index then we return that item.