Stop fibonacci sequence when it reaches a number bigger than 1000 - javascript

I want to make the sequence stop when the last value stored in the array is bigger than 1000.
I have the js code for the sequence and i can make it stop at whatever position i want with the variable limit. But i dont know how to make it stop at a certain number.
The is my code:
let fib = [1,1];
let limit = 20;
function fibonacci(nums) {
let data = [1,1];
for(let i = 2; i < limit; i++) {
nums[i] = nums[i - 1] + nums[i - 2];
data.push(nums[i]);
}
return data;
}
console.log(fibonacci(fib))

You can just use an if condition and break out of the loop as soon as a value is bigger than 1000. In this example I pushed the value and then break out of the loop. You can also break before pushing it to the array
let fib = [1, 1];
let limit = 20;
function fibonacci(nums, breakLimit) {
let data = [1, 1];
for (let i = 2; i < limit; i++) {
nums[i] = nums[i - 1] + nums[i - 2];
if (nums[i] > breakLimit) {
data.push(nums[i]);
break;
} else {
data.push(nums[i]);
}
}
return data;
}
console.log(fibonacci(fib, 1000))

Related

Unsure about syntax/methods. I believe my code should work but it does not

Prompt: Given a positive integer num, return the sum of all odd Fibonacci numbers that are less than or equal to num. The first two numbers in the Fibonacci sequence are 1 and 1. Every additional number in the sequence is the sum of the two previous numbers. The first six numbers of the Fibonacci sequence are 1, 1, 2, 3, 5 and 8. For example, sumFibs(10) should return 10 because all odd Fibonacci numbers less than or equal to 10 are 1, 1, 3, and 5.
The code I wrote for this is:
function sumFibs(num) {
const arr = [1,1];
let sum = 0;
for(let i = 2; i <= num; i++){
let queef = arr[i - 1] + arr[i - 2];
arr.push(queef);
}
for(let j = 0; j < arr.length; j++){
if(arr[j] % 2 != 0){
sum += arr[j];
}
}
return sum;
}
console.log(sumFibs(6));
but i get 23 when it should be 10, I'm not sure why this doesn't work because i feel this would work in java. I have also tried to do arr[i] == queef but that also does not work. I am missing something or should this work?
I think your error relies in
for(let i = 2; i <= num; i++){
I believe you're generating an amount of numbers till num instead of the value itself. Try with something like this (I tried to keep your style):
function sumFibs(num) {
if (num === 1) return 1;
const arr = [1,1];
let sum = 2;
for(let i = 2; i <= num; i++){
let queef = arr[i - 1] + arr[i - 2];
arr.push(queef);
if(arr[i] % 2 != 0 && queef < num){
sum += arr[i];
}
}
return sum;
}
console.log(sumFibs(6));
Welcome Bethany, enjoy your new coding journey. If you change line 4 in your code to:
for(let i = 2; i < num; i++){
it returns 10
It should be < num in the first for loop. Since array indexes start from 0 and not 1, when you type <= 6 it makes an array with 7 numbers in it.

Smallest Common Multiple [Javascript Challenge]

Question: Find the smallest common multiple of the provided parameters that can be evenly divided by both, as well as by all sequential numbers in the range between these parameters.
The range will be an array of two numbers that will not necessarily be in numerical order.
For example, if given 1 and 3, find the smallest common multiple of both 1 and 3 that is also evenly divisible by all numbers between 1 and 3, i.e. divisible by 1, 2 and 3. The answer here would be 6.
function smallestCommons(arr) {
var max=Math.max(...arr);
var min=Math.min(...arr);
var flag = 0;
var i = min;
while(true)
{for(var j=min;j<=max;j++)
{if(i%j!=0)
{flag=1;
break;}
}
if(flag==0)
{flag=5;
break;
}
i++;
}
console.log(i);
}
smallestCommons([1,5]);
For somereason my solution seems to go crazy and go into infinite looping. Although if I initialize var i to 60 (which is the desired output for this specific case i.e.[1,5]) the solution seems to be fine. Any fixes or guesses?
#Kevin has given a pretty good explanation of why it's not working. Your loop will only stop if flag is 0. But once it has been set to 1, you never reset it to 0.
function smallestCommons(arr) {
var max = Math.max(...arr);
var min = Math.min(...arr);
var flag = 0;
var i = min;
while (true) {
for (var j = min; j <= max; j++) {
if (i % j != 0) {
flag = 1;
break;
}
}
if (flag == 0) {
return i; // Return that common value
}
flag = 0; // Reset the flag
i++;
}
}
console.log(smallestCommons([1, 5]));
And here is an alternative way:
function smallestCommons(arr) {
const min = Math.min(...arr),
max = Math.max(...arr),
range = createRange(min, max);
let current = max;
while (true) {
const isFullyDivisible = range.every(n => current % n === 0);
if (isFullyDivisible) {
return current;
}
current++;
}
}
function createRange(min, max) {
return new Array(max - min + 1).fill(null).map((_, i) => min + i);
}
console.log(smallestCommons([1, 3])); // 6
console.log(smallestCommons([5, 1])); // 60
console.log(smallestCommons([1, 10])); // 2520
I did figure out the solution, thanks to the two programming geeks in the main comments sections.
function smallestCommons(arr) {
var max=Math.max(...arr);
var min=Math.min(...arr);
var flag = 0;
var count = 0;
var i = 1;
while(1){
for(var j=min;j<=max;j++)
{if(i%j!=0)
{flag=1;
break;}
if(j==max){
flag=0;
}
}
if(flag==0){
break;
}
i++;
}
console.log(i);
}
smallestCommons([10,2]);

Fill an array with distanced random integers

I need an array to be filled with random integers
Those integers should be very distinct from each other i.e. must at least be 20 units of separation between each items
This is what i have tried so far :
var all = [];
var i = 0;
randomDiff();
function randomDiff() {
var num1 = randomNumber(10, 290); //chose a first random num in the range...
all[0] = num1; //...put it in first index of array
do // until you have 12 items...
{
var temp = randomNumber(10, 290); //...you pick a temporary num
var j;
for (j = 0; j < all.length; j++) // for each item already in the array
{
if ((temp < all[i] - 10) || (temp > all[i] + 10)) // if the temporary num is different enough from others members...
{
all.push(temp); //then you can store it
i++; //increment until....
console.log(all[i]);
}
}
}
while (i < 11) // ...it is filled with 12 items in array
}
////////////Radom in int range function///////////////////////////////////////
function randomNumber(min, max) {
return Math.floor(Math.random() * (max - min) + min);
}
but always unsuccessful, including infinite loops...
Have a look on something like this:
function randomNumber(min, max) {
return Math.floor(Math.random() * (max - min) + min);
}
const LIST_SIZE = 20;
const DISTANCE = 10;
const STOP_AFTER_ATTEMPT = 2000;
const randomList = [];
let attempt = 0;
while(randomList.length < LIST_SIZE && attempt < STOP_AFTER_ATTEMPT) {
const num = randomNumber(10, 290);
const numberExistsWithSmallerDistance = randomList.some(r => Math.abs(r - num) < DISTANCE)
if (!numberExistsWithSmallerDistance) {
randomList.push(num);
}
attempt++;
}
if (randomList.length === LIST_SIZE) {
console.log(randomList);
} else {
console.log("Failed to create array with distnct values after ", attempt, " tries");
}
Here's a solution that will always work, as long as you allow enough room in the range/separation/count you choose. And it's way more efficient than a while loop. It doesn't just keep trying until it gets it right, it actually does the math to make sure it's right the first time.
This comes at the cost of tending to lean towards certain numbers more than others (like from + (i * separation)), so take note of that.
function getSeparatedRadomInts(from, through, separation, count) {
if(through < from) return getSeparatedRadomInts(through, from, separation, count);
if(count == 0) return [];
if(separation == 0) return !!console.log("Please allow enough room in the range/separation/count you choose.");
//pick values from pool of numbers evenly stepped apart by units of separation... adding 1 to from and through if from is 0 so we can divide properly
var smallFrom = Math.ceil((from || 1) / separation);
var smallThrough = Math.floor((through + (from == 0)) / separation);
var picks = randoSequence(smallFrom, smallThrough).slice(-count).sort((a, b) => a - b);
if(picks.length < count) return !!console.log("Please allow enough room in the range/separation/count you choose.");
for (var i = 0; i < picks.length; i++) picks[i] *= separation;
//go through each pick and randomize with any wiggle room between the numbers above/below it... adding 1 to from and through if from is 0
for (var i = 0; i < picks.length; i++) {
var lowerBound = picks[i - 1] + separation || from || 1;
var upperBound = picks[i + 1] - separation || (through + (from == 0));
picks[i] = rando(lowerBound, upperBound);
}
//subtract 1 from all picks in cases where from is 0 to compensate for adding 1 earlier
for (var i = 0; i < picks.length; i++) if(from == 0) picks[i] = picks[i] - 1;
return picks;
}
console.log(getSeparatedRadomInts(10, 290, 20, 12));
<script src="https://randojs.com/1.0.0.js"></script>
To be clear, from is the minimum range value, through is the maximum range value, separation is the minimum each number must be apart from each other (a separation of 20 could result in [10, 30, 50, 70], for example), and count is how many values you want to pick.
I used randojs in this code to simplify the randomness and make it easier to read, so if you want to use this code, just remember to paste this in the head of your HTML document:
<script src="https://randojs.com/1.0.0.js"></script>

I need to create an infinite loop

For my purpose I need to create loop where one variable is looping in this way:
0, 1, 2, 3, 4, 3, 2, 1, 0, 1, 2, 3, 4, 3, 2, 1...
It's look simple but more than hour I wonder how to do it.
My purpose is moving the star in this way
*....
.*...
..*..
...*.
....*
...*.
..*..
.*...
*....
*....
.*...
..*..
...*.
....*
Write that loop as a generator (function *... yield) and then consume it when you need it (for...of). Of course, the consuming code must provide some termination condition.
function* bounce(min, max) {
while (1) {
for (let i = min; i < max; i++)
yield i;
for (let i = max; i > min; i--)
yield i;
}
}
STEPS = 10
for(let x of bounce(0, 4)) {
console.log(x)
if (--STEPS === 0) break;
}
You can use the following code to generate the number pattern that you require. However, you wont be able to run it infinitely since it will crash the browser.
If you want to test, I have added instructions for making the loop infinite.
For you requirement, a larger value for rep variable will be enough.
let min = 0; // Start/min value
let max = 4; // Max value
let dir = 1; // Count direction (+1/-1)
let counter = min; // Your counter variable
let rep = 24; // Remove this line and change condition inside while to true for infinite loop
do {
console.log(counter);
dir = counter===max?-1:counter===min?1:dir;
counter+=dir;
} while (rep-->0); // Change this expression to true for infinite loop
You can use setTimeout or setInterval for doing that:
let number = 0;
let increment = 1;
const from = 0;
const to = 4;
const starDiv = document.getElementById("star");
function printStar(number) {
const text = [0, 1, 2, 3, 4].map(
i => (i === number) ? '*' : '-'
).join('');
starDiv.innerText = text;
}
function loop() {
printStar(number);
number += increment;
if (number == to) {
increment = -1;
} else if (number == from) {
increment = 1;
}
}
const time = 10; // 10 millisecond between step
setInterval(loop, time);
<div id="star">
</div>
You could have a simple counter and then use modulo 8 to get iterations.
let x = (i += direction) % 8;
let y = x > 4 ? 8 - x : x;
This example even prints the ascii art ;)
let i = -1;
let direction = +1;
const out = [
"*....",
".*...",
"..*..",
"...*.",
"....*",
"...*.",
"..*..",
".*...",
"*....",
];
setInterval(function() {
let x = (i += direction) % 8;
let y = x > 4 ? 8 - x : x;
window.document.write(y + " " + out[x] + "<br>");
}, 1000);
(function(min,max,max_loops)
{
for(var loop = 1; loop <= max_loops; loop++, [min,max] = [-max,-min])
{
for(num = min; num < max + (loop == max_loops); num++)
{
console.log(".".repeat(Math.abs(num)) + "*" + ".".repeat(Math.max(Math.abs(max),Math.abs(min)) - Math.abs(num)))
}
}
})(0,4,3)
But since you need an infinite loop, using generator should be more suitable.

Javascript: function to describe array is skipping most of the actual function and returns undefined?

I am trying to write a single javascript function that will take in a list of numbers as arguments and will output the number of odd number, number of negative numbers, will average the numbers, and will output the median. I believe I basically have completed all of the code, but am either confusing my syntax or am incorrectly returning.
Code:
var arrayAnalyze = function(numbers){
var oddNum = []; //Array of odd numbers
var negNum = []; //Array of negative numbers
var numSum = 0; // Sum of all numbers
var avgNum = 0; //Average of all numbers
var midNum = []; //Median number
//Return odd numbers to oddNum array
for (i = 0; i < numbers.length; i++){
if (numbers[i] % 2 !== 0){
oddNum.push(numbers[i]);
}
}
//Return negative numbers to negNum array
for (i = 0; i < numbers.length; i++){
if (Math.abs(numbers[i]) + numbers[i] === 0){
negNum.push(numbers[i]);
}
}
//Return sum of all numbers to numSum variable
for (i = 0; i < numbers.length; i++){
numSum += i;
}
//Return average of numbers to avgNum variable
avgNum = numSum / numbers.length;
//Return median of numbers to midNum array
numbers.sort(function(a,b){return a - b;});
var evenSplit = Math.floor(numbers.length / 2);
if(numbers.length % 2){
midNum = numbers[evenSplit];
}else{
midNum = (numbers[evenSplit - 1] + numbers[evenSplit]) / 2.0; }
midNum.push();
return "Odds: " + oddNum.length, "Negatives: " + negNum.length, "Average: " + avgNum.toFixed(2), "Median: " + midNum[0];
};
console.log(arrayAnalyze(7, -3, 0, 12, 44, -5, 3));
Output:
TypeError: numbers.sort is not a function
There's a number of errors that you'd want to correct - comments inline
var arrayAnalyze = function (numbers) {
var oddNum = []; //Array of odd numbers
var negNum = []; //Array of negative numbers
var numSum = 0; // Sum of all numbers
var avgNum = 0; //Average of all numbers
var midNum = []; //Median number
//Return odd numbers to oddNum array
for (i = 0; i < numbers.length; i++) {
// always check the element at index, i is just the index
if (numbers[i] % 2 !== 0) {
// return exits the currently running function! (not the block)
oddNum.push(numbers[i]);
}
}
//Return negative numbers to negNum array
for (i = 0; i < numbers.length; i++) {
// exclude 0 here
if (Math.abs(numbers[i]) + numbers[i] === 0 && numbers[i]) {
negNum.push(numbers[i]);
}
}
//Return sum of all numbers to numSum variable
for (i = 0; i < numbers.length; i++) {
numSum += numbers[i];
}
//Return average of numbers to avgNum variable
avgNum = numSum / numbers.length;
//Return median of numbers to midNum array
// if you are using a function you need to invoke it to get it's value
midNum.push((function median(numbers) {
// note that this will actually sort the elements of the array you pass in in-place
numbers.sort(function (a, b) { return a - b; });
var evenSplit = Math.floor(numbers.length / 2);
if (numbers.length % 2) {
return numbers[evenSplit];
} else {
return (numbers[evenSplit - 1] + numbers[evenSplit]) / 2.0;
}
})(numbers));
// use + to concatenate the strings, otherwise it just becomes a bunch of comma separated expressions
return "Odds: " + oddNum.length + ",Negatives: " + negNum.length + ",Average: " + avgNum.toFixed(2) + ",Median: " + midNum[0];
};
// an array is passed in using square brackets
console.log(arrayAnalyze([7, -3, 0, 12, 44, -5, 3]));
when a function hits a return statement it will exit out meaning the any code beneath the return will not get executed.
In your odd number sorter you use the %/Modulus on the counter/index rather than numbers[i] to use it on each element of the numbers array parameter. This also needs fixed when you push to the appropriate results array. I have spotted this same concept being done multiple times throughout the function so I would go back and correct that as it would break a couple things.
Also to give you a tip in the right direction in terms of learning return like other users are saying, let's take a look at this part of your code:
for (i = 0; i < numbers.length; i++){
return numSum += i;
}
You do not need to return numSum as your are returning its value later at the end. Just updated the variable you initialized at the beginning by doing the following (also updated in regards to my suggestion above):
for (i = 0; i < numbers.length; i++){
numSum += numbers[i];
}
You cleary are pretty confused about how the return keyword works; I suggest you to check out some documentation here and here.
As an example, you need to change that piece of code
if (numbers % 2 !== 0){
return oddNum.push(numbers);
}else{
return false;
}
into
if (numbers % 2 !== 0){
oddNum.push(numbers);
}
All the others if structures have the same error.
I believe you have a fundamental misunderstand of what return does. MDN has a page on it: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/return#Examples
return interrupts code execution, exits the innermost function and returns a value to the caller.
function myFunction() {
return "foo";
alert("This will never be reached!");
}
alert(myFunction()) // Equivalent to alert("foo").
For example, in your code:
//Return odd numbers to oddNum array
for (i = 0; i < numbers.length; i++){
if (i % 2 !== 0){
return oddNum.push(i); // <- code execution will stop here
}else{
return false; // <- or here, whichever is reached first.
}
}
Which means your loop will never execute for more than one iteration. So when you call
console.log(arrayAnalyze(7, -3, 0, 12, 44, -5, 3));
The first value is odd, so the function will stop at return oddNum.push(i);. And since oddNum.push(i) itself returns nothing (undefined), arrayAnalyze will return undefined too, and the log will be equivalent to
console.log(undefined);
Which is what you are seeing.
In this case the returns are completely unnecessary and the loop should read:
//Return odd numbers to oddNum array
for (i = 0; i < numbers.length; i++){
if (i % 2 !== 0){
oddNum.push(i); // <- now code execution is not interrupted!
}
}
And so on, through the rest of the code.
Also, at the end you declare a function called median:
//Return median of numbers to midNum array
function median(numbers) {
[...]
}
But you never invoke it (calling median(someValue)), which means the code inside it will never be executed either. I haven't checked the code for mathematical correctness, but I believe you should just remove the median declaration and leave its body inside the main arrayAnalyze function.
Your code should look like this :
var arrayAnalyze = function (numbers) {
var oddNum = []; //Array of odd numbers
var negNum = []; //Array of negative numbers
var numSum = 0; // Sum of all numbers
var avgNum = 0; //Average of all numbers
var midNum = []; //Median number
//Return odd numbers to oddNum array
for (i = 0; i < numbers.length; i++) {
if (i % 2 !== 0) {
oddNum.push(numbers[i]);
}
}
//Return negative numbers to negNum array
for (i = 0; i < numbers.length; i++) {
if (Math.abs(numbers[i]) + numbers[i] === 0) {
negNum.push(numbers[i]);
}
}
//Return sum of all numbers to numSum variable
for (numbers[i] = 0; numbers[i] < numbers.length; numbers[i]++) {
numSum += numbers[i];
}
//Return average of numbers to avgNum variable
avgNum = numSum / numbers.length;
//Return median of numbers to midNum array
var newArrayOfNumber = numbers;
newArrayOfNumber.sort();
var evenSplit = Math.floor(newArrayOfNumber.length / 2);
if (newArrayOfNumber.length % 2) {
midNum = newArrayOfNumber[evenSplit];
} else {
midNum = (newArrayOfNumber[evenSplit - 1] + newArrayOfNumber[evenSplit]) / 2.0;
}
return "Odds: " + oddNum.length + ", Negatives: " + negNum.length +", Average: " + avgNum.toFixed(2) +", Median: " + midNum;
};
When you call the function you should pass a array to it, so just add [] to your numbers like this : arrayAnalyze([7, -3, 0, 12, 44, -5, 3])
it should return :"Odds: 3, Negatives: 3, Average: 3.50, Median: 7.5"
When you want to add some number to a array in a for block or a if block, dont use return, just do the operation and if you want to break the for loop, use the line :
Break;
and when you want to access the number in your for loop, you should call the array and not only the i, like this : number[i]
espering that it help you
sorry for my mistakes in writting in english

Categories

Resources