Задачи для решения

На работу с функциями

Если переменная a больше нуля - то в ggg запишем функцию, которая выводит один !, иначе запишем функцию, которая выводит два !.

Решение:

var a;
if (a > 0) {
	var ggg = function() {
		console.log('!');
	}
} else {
	var ggg = function() {
		console.log('!!');
	}
} 

Функция ggg принимает 2 параметра: число и анонимную функцию, которая возводит число в квадрат. Возведите число в 4-тую степень с помощью ggg.

Решение:

var ggg = function(n, f) {return f(n);}
funcNew = function(a){return Math.pow(a, 2)};
num = 7;
alert(ggg( (ggg(num, funcNew)), funcNew));

Функция ggg принимает 2 параметра: анонимную функцию, которая возвращает 3 и анонимную функцию, которая возвращает 4. Верните результатом функции ggg сумму 3 и 4.

Решение:

var ggg = function(a, b){return a() + b();};
var f1 = function(){return 3};
var f2 = function(){return 4};
console.log(ggg(f1, f2));

Дана функция ggg. Она требует первым параметром число, вторым функцию, которая возводит в квадрат, а третьим параметром функцию, которая возводит в куб. Эти функции есть как Function Declaration - kvadrat, kub. Пусть функция ggg вернет сумму квадрата и куба числа.

Решение:

var ggg = function(a, b, c){return b(a) + c(a);};
var square = function(n){return Math.pow(n, 2)};
var cub = function(n){return Math.pow(n, 3)};
console.log(ggg(3, square, cub));

Сделайте функцию each, которая первым параметром принимает массив, а вторым - функцию, которая применится к каждому элементу массива. Функция each должна вернуть измененный массив.

Решение:

var each = function(startArr, f){return f(startArr)};
var arr = [64, 49, 36, 25, 16];
var myFunc = function(a){
	var newArr = [];
	for (var i = 0; i < a.length; i++) {
		newArr[i]=Math.sqrt(a[i]);
	}
	return newArr;
}
document.write(each(arr, myFunc));

Сделайте функцию each, которая первым параметром принимает массив, а вторым - массив функций, которые по очереди применятся к каждому элементу массива: к первому элементу массива - первая функция, ко второму - вторая и так далее пока функции в массиве не закончатся, после этого возьмется первая функция, вторая и так далее по кругу.

Решение:

var each = function(numArr, funcArray) {
	var newArr = [];
	for (var i = 0; i < numArr.length; i++){
		var current = funcArray[i % funcArray.length](numArr[i]);
		funcArray.length через j++;
		newArr.push(current);
  	}
	return newArr
}

var f1 = function(a){return a + 3};
var f2 = function(a){return a + 2};
var f3 = function(a){return a + 1};
var funcAll = [f1, f2, f3];
var startArray = [0,1,2, 3, 4, 5, 6, 7, 8, 9,10, 11];
document.write(each(startArray, funcAll));

На замыкания

Сделайте функцию, которая считает и выводит количество своих вызовов.

func(); //выведет 1
func(); //выведет 2
func(); //выведет 3
func(); //выведет 4

Решение:

function counter() {
	var i = 1;
	return function() {return i++};
}

var func = counter();

console.log(func());
console.log(func());
console.log(func());

Даны кнопки. Привяжите к каждой кнопке событие по клику, которое будет считать количество нажатий по кнопке и выводить его в текст кнопки. Количество нажатий для каждой кнопки должно хранится в замыкании.

Решение:

<button>0</button>
<button>0</button>
<button>0</button>     
var f1 = function(){
	var k = 1;
	return function() {
		this.innerHTML = k;
		return k++;
	}
}

var all_buttons = document.getElementsByTagName('button');
for (var i = 0; i < all_buttons.length; i++) {
	all_buttons[i].addEventListener('click', f1(this));
}

Дан массив цветов. Даны абзацы. По первому нажатию на абзац он должен покраситься в первый цвет из массива, по второму нажатию - во второй и так далее. Все абзацы работают независимо.

Решение:

<p>Текст1</p>
<p>Текст2</p>
<p>Текст3</p>     
var colors = ['magenta', 'cyan', 'firebrick', 'springgreen', 'skyblue'];
var p_collect = document.getElementsByTagName('p');

var f1 = function() {
	var k = 0;
	return function() {
		this.style.color = colors[k];
		k++;
		if (k == colors.length){k=0};
	}
}

for (var i = 0; i < p_collect.length; i++) {
	p_collect[i].addEventListener('click', f1());
}

Даны кнопки. Каждая кнопка по нажатию на нее выводить следующее число Фибоначчи. Кнопки работают независимо. Решить через замыкания.

Решение:

<button>Фибоначчи</button><span></span>
<button>Фибоначчи</button><span></span>
<button>Фибоначчи</button><span></span>     
var f1 = function(){
	var a = 0;
	var b = 1;
	var temp;
	return function() {
		this.nextElementSibling.innerHTML = a;
		temp = a;
		a = b;
		b = temp +a;
	}
}

var buts_collect = document.getElementsByTagName('button');
for (var i = 0; i < buts_collect.length; i++) {
	buts_collect[i].addEventListener('click', f1());
}

Даны инпуты. Сделайте так, чтобы каждый инпут хранил историю своих изменений. Каждый инпут свою. Изменением считается событие onchange. История должна хранится в замыкании. Над каждым инпутом должны быть стрелочки назад и вперед, с помощью которых можно передвигаться по истории.

Решение:

<div id="conteiner">
	<div>
		<button>←</button><button>→</button>
		<input /></div>
		<div>
		<button>←</button><button>→</button>
		<input /></div>
 	</div>
</div>      

Сделайте функцию, каждый вызов который будет генерировать случайные числа от 1 до 100, но так, чтобы они не повторялись, пока не будут перебраны все числа из этого промежутка. Решите задачу через замыкания - в замыкании должен хранится массив чисел, которые уже были сгенерированы функцией.

Решение:

<button>Жми</button>
<p></p>      
var f1 = function() {
	var already_used = [];
	return function() {
		var new_num = Math.floor(Math.random() * 100 + 1);
		for (var i = 0; i < already_used.length; i++) {
			if (already_used[i] == new_num) {return}
		};

		parag.innerHTML += new_num+', ';
		already_used.push(new_num);
	}
}

var but = document.querySelector('button').addEventListener('click', f1());
var parag = document.querySelector('p');