2017-06-08 32 views
1

我有一个集合,我想从中获取一些值,并将它们合并在一起形成一个新的值。到目前为止,我已经看了R.evolve,但没有运气(因为medias也是一个集合并字段的对象来创建Ramda的新字段

这是我开始用:

[{ 
    "permalink": "http://example.com/1", 
    "medias": [{ 
    "filename": "image_1.png", 
    }] 
}, { 
    "permalink": "http://example.com/3", 
    "medias": [{ 
    "filename": "image_3.png", 
    }] 
}] 

这就是想什么我给结尾:

[{ 
    "permalink": "http://example.com/1", 
    "medias": [{ 
    "filename": "image_1.png", 
    "image_url": "http://example.com/1/image_1.png" 
    }] 
}, { 
    "permalink": "http://example.com/3", 
    "medias": [{ 
    "filename": "image_3.png", 
    "image_url": "http://example.com/3/image_3.png" 
    }] 
}] 

从本质上讲就是我们正在做的是在前面加上每个filenamepermalink

这是第k。 ind我到目前为止的事情,不幸的是,当运行medias上的转换时,我无法访问permalink属性。

const mapMedia = R.map(
    // can’t get access to the `permalink` in here? 
) 

const transformations = { 
    medias: mapMedia 
} 

const transform = R.compose(
    R.map(R.evolve(transformations)), 
)(data) 
+0

你能告诉我们你的”到目前为止尝试过吗? –

+0

@ScottSauyet当然!到目前为止,我刚刚加入了我的尝试。 – gosseti

回答

2

所以问题是,你需要的数据不在范围内。在我看来,解决这个问题的最简单方法是添加一些范围!

首先,您不需要拨打compose,因为您只能提供一种功能。因此,我们可以将其替换

const transform = R.compose(
    R.map(R.evolve(transformations)), 
)(data) 

只是

const transform = R.map(R.evolve(transformations)), 

(我也删除通话与(data),因为我试图建立这件事作为一个可重复使用的功能。我们会再后来用它打电话。transform(data)

现在我们要添加上下文,以便transformations有范围的对象,我们可以做到这一点是这样的:

const transform = R.map(image => R.evolve(transformations(image), image)); 

当然,这意味着transformations需要改变,以考虑到这一点。我们可以这样做:

const transformations = image => ({ 
    medias: mapMedia(image.permalink) 
}) 

...而这又需要更改为mapMedia。我认为它应该只需要知道固定链接而不是整个图像,所以我们只能通过如上所述。而现在mapMedia是这样的:

const mapMedia = permalink => R.map(
    medium => // do something with `medium` and `permalink` 
); 

有很多方法,你可以做到这最后一步。他们中的一个,相当一致您使用的evolve会是这样:

const mapMedia = permalink => R.map(
    medium => assoc('image_url', permalink + '/' + medium.filename, medium) 
); 

另一种方法既evolveassoc是调查Ramda各种lens - 相关功能,如lensPropoverset

现在,如果这些辅助函数仅用于此目的,您可能不希望它们混乱起来,并且可以选择将它们内联到主函数中。如果你喜欢,你可能所有上述合并成

const addUrls = map(
    image => evolve({ 
    medias: map(medium => assoc('image_url', image.permalink + '/' + medium.filename, medium)), 
    }, image) 
); 

你可以看到separate functions方法或Ramda REPL的combined one。对于好的措施,还有一个version using lenses


(和一个单独的说明,单词“媒体”已经是复数。单数为“中等”。有对“媒体”没有充分的理由。)

+0

非常感谢你为这个彻底而优秀的答案。这是我喜欢使用拉姆达的原因之一! – gosseti