函数式编程 - 递增计数器的简单 For 循环
Functional Programming - Simple For Loop For Incrementing Counter
我们在函数式编程中不使用 for loop
,而是使用 higher order functions
,如 map、filter、reduce 等。这些非常适合遍历数组。
但是,我想知道如何做一个简单的计数器循环。
let i = 0;
for( i; i < 10; i++) {
console.log( "functional programming is a religion")
};
那么,如何在函数式编程中做到这一点?
So, how would one do this in functional programming?
其实作用不大,你还是可以用forEach
加一点workaround
Array.apply(null, Array(5)).forEach(function(){
console.log( "funtional programming is a religion")
});
5 是你要迭代的次数。
使用简单的递归函数
function counter(value) {
var i = value;
if(i<10){
console.log( "functional programming is a religion");
}else{
return;
}
counter(++i);
}
counter(0);
这个怎么样?
/*forLoop takes 4 parameters
1: val: starting value.
2: condition: This is an anonymous function. It is passed the current value.
3: incr: This is also an anonymous function. It is passed the current value.
4: loopingCode: Code to execute at each iteration. It is passed the current value.
*/
var forLoop = function(val, condition, incr, loopingCode){
var loop = function(val, condition, incr){
if(condition(val)){
loopingCode(val);
loop(incr(val), condition, incr);
}
};
loop(val, condition, incr);
}
然后调用循环如下:
forLoop(0,
function(x){return x<10},
function(x){return ++x;},
function(x){console.log("functional programming is a religion")}
);
输出:
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
请告诉我您对这个答案的看法。
为什么不为数字构建一个高阶函数。
Number.prototype.repeat = function (fn) {
var i,
n = Math.abs(Math.floor(this)) || 0;
for (i = 0; i < n; i++) fn(i, this);
};
(10).repeat(function (i, n) { document.write(i + ' of ' + n + ': your claim<br>'); });
(NaN).repeat(function (i, n) { document.write(i + ' of ' + n + ': your claim<br>'); });
函数式方法是编写一个 HOF,它创建一个调用基础函数 n 次的函数:
function repeatTimes(fn, n) {
return function() {
while (n--) fn(...arguments);
};
}
现在您可以按如下方式调用您的函数:
function myFunc() { console.log("functional programming is a religion"); }
const tentimes = repeatTimes(myFunc, 10);
tentimes();
可以通过概括继续重复调用的条件来扩展此方法。我们将传递一个确定何时停止的函数,而不是固定数字 n。我们将向该函数传递迭代计数:
function repeatWhile(fn, cond) {
return function() {
var count = 0;
while (cond(count++)) fn(...arguments);
};
}
现在我们称之为
const tentimes = repeatWhile(myFunc, i => i < 10);
tentimes();
我们可以通过一个创建条件函数的函数进一步简化这个过程,我们称之为 lessThan
:
function lessThan(n) { return i => i < n; }
现在调用可以写成
const tentimes = repeatWhile(myFunc, lessThan(10));
tentimes();
重点是使大部分代码可测试。对于您的示例,我想最好是创建文本而不打印它。
function unFold(fnStopPredicate, fnTerm, fnGenerate, aSeed) {
var arr = [];
while( ! fnStopPredicate(aSeed) ){
arr.push(fnTerm(aSeed));
aSeed = fnGenerate(aSeed);
}
return arr;
}
您可能会说这不是功能性的,这是真的,但它有一个功能性界面。它不会改变它的参数并且返回的值始终是它的初始参数的直接结果。
var strValues = unFold(x => x > 10,
x => "functional programming is a religion",
x => x+1,
0).join("\n");
// Real side effect goes here
console.log(strValues);
这里的要点是,只要您提供的函数本身不产生副作用,您就可以对 unFold 的使用进行单元测试。
不要使用 'while' 或 'for' 来控制命令式编程的流程而不是函数式。
Array(10).fill("functional programming is not a religion")
.map((msg) => {
console.log(msg);
return msg;
});
此函数调用 callbackFn count 次。
const times = (count, callbackFn) => {
if (count === 0) {return}
callbackFn();
times(count-1, callbackFn);
}
times(10, () => console.log("Functional Programming is a Religion"));
此函数的工作方式类似于 for 循环
const forLoop = (initialValues, conditionFn, newValsFn, bodyFn) => {
if (!conditionFn(initialValues)) {return}
bodyFn(initialValues);
forLoop(newValsFn(initialValues), conditionFn, newValsFn, bodyFn);
}
forLoop({i: 0}, ({i}) => i < 10, ({i}) => ({i: i+1}), ({i}) => {
console.log(i, "Functional Programming is a Religion.");
});
此处,上述函数用于打印斐波那契数列的前 n 项
const forLoop = (initialValues, conditionFn, newValsFn, bodyFn) => {
if (!conditionFn(initialValues)) {return}
bodyFn(initialValues);
forLoop(newValsFn(initialValues), conditionFn, newValsFn, bodyFn);
}
const fibPrint = (n) => {
let n1 = 0, n2 = 1, nextTerm;
forLoop({i: 1}, ({i}) => i <= n, ({i}) => ({i: i+1}), () => {
console.log(n1);
nextTerm = n1 + n2;
n1 = n2;
n2 = nextTerm;
});
}
fibPrint(10);
当迭代次数很大时,在函数中调用同一个函数需要大量内存。进一步 cpu 时间也增加了。 intel、arm等公司
会喜欢这种方法,因为他们正在鼓动软件公司推出
资源匮乏的程序
不管怎么说,现在我们进入了需要猛犸象来解决问题的人工智能时代,我认为这不是问题。我正在教微处理器和微控制器,我的担心可能是因为这个。
努尔
您还可以使用 some()
或 every()
来中断或继续您的功能循环。
像这个例子,我使用 some()
继续 return false
和 return true
中断。
Array(10).fill("message").some((msg,index) => {
//like continue loop
if(index === 5) return false
//like break loop
if(index === 9) return true
console.log(msg, index)
})
我们在函数式编程中不使用 for loop
,而是使用 higher order functions
,如 map、filter、reduce 等。这些非常适合遍历数组。
但是,我想知道如何做一个简单的计数器循环。
let i = 0;
for( i; i < 10; i++) {
console.log( "functional programming is a religion")
};
那么,如何在函数式编程中做到这一点?
So, how would one do this in functional programming?
其实作用不大,你还是可以用forEach
加一点workaround
Array.apply(null, Array(5)).forEach(function(){
console.log( "funtional programming is a religion")
});
5 是你要迭代的次数。
使用简单的递归函数
function counter(value) {
var i = value;
if(i<10){
console.log( "functional programming is a religion");
}else{
return;
}
counter(++i);
}
counter(0);
这个怎么样?
/*forLoop takes 4 parameters
1: val: starting value.
2: condition: This is an anonymous function. It is passed the current value.
3: incr: This is also an anonymous function. It is passed the current value.
4: loopingCode: Code to execute at each iteration. It is passed the current value.
*/
var forLoop = function(val, condition, incr, loopingCode){
var loop = function(val, condition, incr){
if(condition(val)){
loopingCode(val);
loop(incr(val), condition, incr);
}
};
loop(val, condition, incr);
}
然后调用循环如下:
forLoop(0,
function(x){return x<10},
function(x){return ++x;},
function(x){console.log("functional programming is a religion")}
);
输出: 函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
函数式编程是一种信仰
请告诉我您对这个答案的看法。
为什么不为数字构建一个高阶函数。
Number.prototype.repeat = function (fn) {
var i,
n = Math.abs(Math.floor(this)) || 0;
for (i = 0; i < n; i++) fn(i, this);
};
(10).repeat(function (i, n) { document.write(i + ' of ' + n + ': your claim<br>'); });
(NaN).repeat(function (i, n) { document.write(i + ' of ' + n + ': your claim<br>'); });
函数式方法是编写一个 HOF,它创建一个调用基础函数 n 次的函数:
function repeatTimes(fn, n) {
return function() {
while (n--) fn(...arguments);
};
}
现在您可以按如下方式调用您的函数:
function myFunc() { console.log("functional programming is a religion"); }
const tentimes = repeatTimes(myFunc, 10);
tentimes();
可以通过概括继续重复调用的条件来扩展此方法。我们将传递一个确定何时停止的函数,而不是固定数字 n。我们将向该函数传递迭代计数:
function repeatWhile(fn, cond) {
return function() {
var count = 0;
while (cond(count++)) fn(...arguments);
};
}
现在我们称之为
const tentimes = repeatWhile(myFunc, i => i < 10);
tentimes();
我们可以通过一个创建条件函数的函数进一步简化这个过程,我们称之为 lessThan
:
function lessThan(n) { return i => i < n; }
现在调用可以写成
const tentimes = repeatWhile(myFunc, lessThan(10));
tentimes();
重点是使大部分代码可测试。对于您的示例,我想最好是创建文本而不打印它。
function unFold(fnStopPredicate, fnTerm, fnGenerate, aSeed) {
var arr = [];
while( ! fnStopPredicate(aSeed) ){
arr.push(fnTerm(aSeed));
aSeed = fnGenerate(aSeed);
}
return arr;
}
您可能会说这不是功能性的,这是真的,但它有一个功能性界面。它不会改变它的参数并且返回的值始终是它的初始参数的直接结果。
var strValues = unFold(x => x > 10,
x => "functional programming is a religion",
x => x+1,
0).join("\n");
// Real side effect goes here
console.log(strValues);
这里的要点是,只要您提供的函数本身不产生副作用,您就可以对 unFold 的使用进行单元测试。
不要使用 'while' 或 'for' 来控制命令式编程的流程而不是函数式。
Array(10).fill("functional programming is not a religion")
.map((msg) => {
console.log(msg);
return msg;
});
此函数调用 callbackFn count 次。
const times = (count, callbackFn) => {
if (count === 0) {return}
callbackFn();
times(count-1, callbackFn);
}
times(10, () => console.log("Functional Programming is a Religion"));
此函数的工作方式类似于 for 循环
const forLoop = (initialValues, conditionFn, newValsFn, bodyFn) => {
if (!conditionFn(initialValues)) {return}
bodyFn(initialValues);
forLoop(newValsFn(initialValues), conditionFn, newValsFn, bodyFn);
}
forLoop({i: 0}, ({i}) => i < 10, ({i}) => ({i: i+1}), ({i}) => {
console.log(i, "Functional Programming is a Religion.");
});
此处,上述函数用于打印斐波那契数列的前 n 项
const forLoop = (initialValues, conditionFn, newValsFn, bodyFn) => {
if (!conditionFn(initialValues)) {return}
bodyFn(initialValues);
forLoop(newValsFn(initialValues), conditionFn, newValsFn, bodyFn);
}
const fibPrint = (n) => {
let n1 = 0, n2 = 1, nextTerm;
forLoop({i: 1}, ({i}) => i <= n, ({i}) => ({i: i+1}), () => {
console.log(n1);
nextTerm = n1 + n2;
n1 = n2;
n2 = nextTerm;
});
}
fibPrint(10);
当迭代次数很大时,在函数中调用同一个函数需要大量内存。进一步 cpu 时间也增加了。 intel、arm等公司 会喜欢这种方法,因为他们正在鼓动软件公司推出 资源匮乏的程序
不管怎么说,现在我们进入了需要猛犸象来解决问题的人工智能时代,我认为这不是问题。我正在教微处理器和微控制器,我的担心可能是因为这个。 努尔
您还可以使用 some()
或 every()
来中断或继续您的功能循环。
像这个例子,我使用 some()
继续 return false
和 return true
中断。
Array(10).fill("message").some((msg,index) => {
//like continue loop
if(index === 5) return false
//like break loop
if(index === 9) return true
console.log(msg, index)
})