使用对象中的ramda函数进行搜索

时间:2016-12-13 18:32:50

标签: javascript ramda.js

我有以下代码:

const trimString = (s) => s.trim()
const compareObjects = (o1, o2) => equals(o1, o2)
const itemExists = (haystack, needle) => contains(haystack, needle)

const objects = [
  { duration: '0.360000', name: 'Arthur', time: '0.660000',   paragraph: 'p0-0' },
  { duration: '0.150000', name: 'the',    time: '1.020000',   paragraph: 'p0-0' },
  { duration: '0.380000', name: 'rat',    time: '1.170000',   paragraph: 'p0-0' },
  { duration: '0.770000', name: '.',      time: '1.550000',   paragraph: 'p0-0' },
  { duration: '0.360000', name: 'Arthur', time: '89.820000',  paragraph: 'p1-0' },
  { duration: '0.390000', name: 'stood',  time: '90.180000',  paragraph: 'p1-0' },
  { duration: '0.090000', name: 'and',    time: '90.570000',  paragraph: 'p1-0' }
];

function searchFor(toSearch) {
  var results = [];
  toSearch = trimString(toSearch); // trim it
  for(var i=0; i<objects.length; i++) {
    for(var key in objects[i]) {
      if(objects[i][key].indexOf(toSearch)!=-1) {
        if(!itemExists(results, objects[i])) results.push(objects[i]);
      }
    }
  }
  return results;
}

log(searchFor('Arthur'))

我得到了结果:

[
    {
        duration: '0.360000',
        name: 'Arthur',
        time: '0.660000',
        paragraph: 'p0-0'
    },
    {
        duration: '0.360000',
        name: 'Arthur',
        time: '89.820000',
        paragraph: 'p1-0'
    }
]

但是如果我使用p0-0

,我仍然坚持如何将其变成ramda函数并且能够添加多个搜索项并仅显示Arthur the的结果

非常感谢任何建议。

1 个答案:

答案 0 :(得分:0)

在接近功能样式时,有助于我从最基本的要求中慢慢构建完整的规范。要求不明确,但似乎您想要返回一个与名称匹配的对象,并且可能扩展此功能,以便您可以传入一组名称并返回一个对象数组。

因此,让我们从最基本的要求开始,即根据名称是否与给定参数匹配来返回布尔值。为此,我们将使用函数propEq

const nameEq = pred => R.propEq('name', pred)

// This is just a partially application of:
// const nameEq = pred => obj => R.propEq('name', pred)(obj)

现在要查找列表中匹配的所有对象,我们使用函数filter,它将返回所提供函数的任何求值为true的元素

const nameInList = pred => R.filter(nameEq(pred))

// This is again a partial application of:
// const nameInList = pred => obj => R.filter(nameEq(pred))(obj)

然后可以使用

调用它
nameInList('Arthur')(objects)

返回

[
  {
    "duration": "0.360000",
    "name": "Arthur",
    "paragraph": "p0-0",
    "time": "0.660000"
  },
  {
    "duration": "0.360000",
    "name": "Arthur",
    "paragraph": "p1-0",
    "time": "89.820000"
  }
]

或者我们可以部分应用我们的功能

const findArthur = nameInList('Arthur')

然后传入我们的对象列表

findArthur(objects)

然后我们可以通过定义:

来进一步扭转参数
const flipped = R.compose(R.curry, R.flip(R.uncurryN(2, nameInList)))

这将允许我们将函数部分应用于objects,并通过传入字符串来简单地查找名称。