你如何使用lodash链接函数?

时间:2016-02-23 23:44:28

标签: javascript lodash

我有一个看起来像

的对象
var foundUser = {
    charData: []
}

然后我使用mysql从数据库加载一个对象,然后我调用

_.assignIn(foundUser, rows[0]);

但是我得到了一些我不需要的额外属性(使用select无法解决这个问题)

所以我打电话给

foundUser = _.omit(foundUser, ['blah']);

但是,如果我能做的话,那将是件好事。

_.assignIn(foundUser, rows[0]).omit(rows[0], ['blah']);

但是这会引发错误,我做错了还是还有另外一种方法可以做到这一点?

4 个答案:

答案 0 :(得分:63)

要使用lodash链接,首先必须包装对象:

_(foundUser).assignIn(rows[0]).omit(['blah']).value();

进一步澄清:

_创建一个允许隐式方法链接的lodash对象。隐式方法链接意味着在某些情况下它可能返回原始值,而在其他情况下,它可能会返回一个需要通过调用.value()来解包的lodash对象。

如果你使用_.chain(...),你将使用显式方法链创建一个lodash对象。结果总是一个包装值,并且总是需要通过调用.value()来解包。

这里有进一步参考的文档链接:

Explicit chaining in Lodash

Implicit chaining in Lodash

答案 1 :(得分:19)

作为换行链解开模式的替代方案(没有任何内在错误,但替代方案总是很有趣),还有另一种方法可以检查。

尝试利用_.flow

我们的想法是flow内的每个函数都会接收前一个函数作为输入,这正是您所需要的。 举个例子,给出了这个数据:

var foundUser = {
    charData: []
};

var rows = [{ok: 1, blah: 'nope'}];

使用Lodash FP我们可以将数据作为最后一个参数传递。此功能以及Lodash / fp中每种方法的自动调整功能使我们在编写功能时更轻松。这意味着我们可以拥有这种简洁而富有表现力的代码:

_.flow(
 _.assign(rows[0]),
 _.omit('blah')
)(foundUser);

// >> {"charData":[],"ok": 1}

使用Lodash的标准版本,我们必须使用_.partial自己来理解这些函数,代码肯定看起来不那么简洁,但仍然可以这样做:

_.flow(
 _.partialRight(_.assign, rows[0]),
 _.partialRight(_.omit, 'blah')
)(foundUser);

// >> {"charData":[],"ok": 1}

使用流而不是链接的一个好处是,您可以轻松地将Lodash方法与 您自己的自定义函数 混合使用,因为 - 如上所述 -  他们所需要的只是数据作为输入和数据作为输出,而不是其他:

const yourFunction = d => ({ ...d, yourProp: 4 });

_.flow(
 _.assign(rows[0]),
 yourFunction,
 _.omit('blah')
)(foundUser);

// >> {"charData":[],"ok": 1, yourProp: 4}

这使得函数组合更容易,更灵活,并且可以说自然会导致更具表现力的代码。

另一件需要注意的事情。如果您只安装和导入您使用的Lodash方法,则必须添加flow包而不是整个Lodash库,因为您要进行链接。

npm i --save lodash.flow

Vs的

npm i --save lodash

在许多真实世界的应用程序中,拥有Lodash的完整版本并不是一个问题并且可以说更容易维护更新,这可能是一个可以忽略不计的优势,但是如果您正在编写将要分发的库或脚本,则非常方便用作第三方工具。在这种情况下,您将能够在分布式大小方面降低您的足迹。

Lodash方法docs:

两篇值得一试的文章:

NB - 我认为第二篇文章的标题有点苛刻,但不要跳过它,内容确实非常丰富。

其他一些注意事项:

  • 在Lodash / fp Flow中,别名为_.pipe,因此您可以根据自己的喜好选择。

  • 如果您希望从左到右合成,也可以使用_.flowRight(或其fp别名_.compose),如Ramda's compose中所示。

示例:

_.flow(
 _.assign(rows[0]), // #1st to execute
 yourFunction,  // #2
 _.omit('blah'),  // #3
)(foundUser);

// is the same as...

_.flowRight(
 _.omit('blah'), // #3rd to execute
 yourFunction, // #2
 _.assign(rows[0]), // #1
)(foundUser);

答案 2 :(得分:5)

你有没有试过lodash/fp?它具有所有相同的功能,但它们都是curry,它们都没有改变输入。

因此,你可以用一种非常好的方式组成它们。

示例:

import moment from 'moment'
import { compose, filter, groupBy, size, sortBy } from 'lodash/fp'

const fromAdmin = filter({ type: 'admin' })
const groupedByDate = groupBy(message => moment(message.createdAt).format('YYYYMMDD'))
const sorted = sortBy('createdAt')
const unreadByUser = filter({ isReadByUser: false })

const groupedMessages = compose(
  groupedByDate,
  sorted,
  unreadByUser,
  fromAdmin,
)(messages)

答案 3 :(得分:1)

链是Lodash中与管道的最佳等效项。

_.chain(foundUser)
 .assignIn(rows[0])
 .omit(['blah'])
 .value()

您还可以通过.tap.thru链接某些自定义函数,例如:

_.chain(foundUser)
 .assignIn(rows[0])
 .tap(console.log)
 .omit(['blah'])
 .value()