我正在开始或试图学习函数式编程monad。
所以第一个也许是。我正在尝试用monad转换代码。
function(fieldName, vals, fields) {
var newValue = vals[fieldName];
if (typeof(newValue) == 'undefined') {
var elemFrom = fields[fieldName];
if (elemFrom) {
newValue = fields[fieldName]
}
}
if (typeof (newValue) != 'undefined') {
return newValue
}
}
在这里,我有一堆未定义的支票,我认为这是对monay的很好使用。
我的问题是我读到您将值传递给了monad和map函数。
但是,就我而言,我替换了monad中的值。
如果我传递null,则由于值未定义,因此map方法将不会显示。
我没有使用框架,我想要简单的实现,以便我能理解它。
是否应该在monad类(函数)中添加“ else”方法。
我遇到了相反的情况“如果值未定义,请执行一些操作”
您能建议解决问题的方法吗
谢谢
答案 0 :(得分:1)
因此您发布的功能可以重写为
const f = (a, b, c) => b[a] === undefined ? c[a] : b[a];
我不清楚这完全是一个函数,而不是在要使用相关对象属性的任何地方都内联,但是也许您只是部分应用它,或者我没有判断。
对于Maybe,一个(非常简单的)实现可能看起来像这样:
class Maybe {
static of (value) {
return new Maybe(value);
}
// Proper solution here should be recursive to handle
// nesting properly, but I'm lazy
static equals (a, b) {
return a.chain(x => x) === b.chain(x => x);
}
constructor(value) {
this._value = value;
}
map (f) {
// Does not distinguish null from undefined, but YMMV. Note
// that if the Maybe value is null or undefined we never touch
// f, that's the null propagation thing.
return this._value == null ? this : new Maybe(f(this._value));
}
chain (f) {
const result = this._value == null ? this : f(this._value);
console.assert(result instanceof Maybe);
return result;
}
}
现在我们可以测试它是否符合Monad法律:
const a = 3;
const f = x => Maybe.of(x * x);
Maybe.of(a).chain(f) === f(a) // left identity
Maybe.equals(Maybe.of(5).chain(Maybe.of), Maybe.of(5)); // right identity
那是有效的仿函数
Maybe.equals(Maybe.of(3).map(x => x), Maybe.of(3)); // identity
Maybe.equals( // composition
Maybe.of(3).map(x => x + 2).map(x => x * 3),
Maybe.of(3).map(compose(x => x * 3, x => x + 2))
);
甜。
现在,开始执行您的功能。它将被重写为
const f = (a, b, c) => {
return b[a] === undefined ? Maybe.of(c[a]) : Maybe.of(b[a]);
}
也许您现在看到我感到困惑的原因,也许在这里并没有为您节省很多。但是,如果我使用的是Maybe,我会像这样重写整个内容:
const or = (a, b) => {
return Maybe.of(a == null ? b : a);
}
然后我只需传递属性访问权限即可:
const obj1 = { a: 2, c: 3 };
const obj2 = { b: 4 };
const prop = "a"
const result = or(obj1["prop"], obj2["prop"]); // Maybe(2)
在评论中提醒我有关替代的@Bergi。您可以像上面这样向Maybe类添加方法:
alt (x) {
if (!(x instanceof Maybe)) {
throw new TypeError("Expected a Maybe");
}
return this.chain(x => x) == null ? x : this;
}
// semantics
Maybe.of(null).alt(Maybe.of(3)); // Maybe(3)
Maybe.of(2).alt(Maybe.of(4)); // Maybe(2)
// usage
Maybe.of(obj1[prop]).alt(Maybe.of(obj2[prop]));
请注意,这不能完全满足Alternative的实现(您还需要一个零/空方法),但是您可以阅读here和here以获得更多详细信息。这可能是您发布的功能的最佳替代品。