我目前有一个user
对象,其上有一个currentRoom()
方法,有时可能不存在或返回null
。
如果currentRoom()
方法返回了某些内容,那么我需要在其上调用messages()
方法。如果两者都没有返回任何内容,我想返回一个默认的空数组[]
。
我想使用Ramda在功能上解决这个问题,所以它很整洁且可重复使用。目前,我的(非Ramda)代码如下所示:
const user = Users.findOne({ username: params.id })
const room = (user.currentRoom && user.currentRoom() || {})
const messages = (room.messages && room.messages() || [])
我想的某种逻辑是传递所需方法的列表,以及默认结果,如果没有任何结果。
/* getMessages(defaultIfNull, methodsArray, object) */
getMessages([], ['currentRoom', 'messages'], user)
基本上与pathOr
类似,但对于对象上的方法。
答案 0 :(得分:5)
我想我会像Option
一样使用const getRoom = user => "currentRoom" in user ? [user.currentRoom()] : [];
const getMessages = room => "messages" in room ? room.messages() : [];
const allTogether = R.compose(R.chain(getMessage), R.chain(getRoom), R.of);
console.log(allTogether(Users.findOne({ username: params.id })));
monad:
def float_check(s):
try:
float(s)
return True
except ValueError:
return False
l = ['1', '2', '2.1', 'ab1', '1ab']
print([i for i in l if float_check(i)])
答案 1 :(得分:0)
您可以使用仅使用Ramda的无点解决方案。首先,我们定义一个withDefaults
函数,它将在对象中设置currentRoom
和messages
方法,这些方法是未定义的。
var withDefaults = R.pipe(
// if don't have `currentRom` add a
// `currentRom` function that returns an empty object
R.unless(
R.hasIn('currentRoom'),
R.assoc('currentRoom',
R.always({}))),
// if don't have `messages` add a
// `messages` function that returns an empty array
R.unless(
R.hasIn('messages'),
R.assoc('messages',
R.always([]))))
此功能可根据需要过滤对象设置方法。用法示例。
var user = withDefaults(getById(id))
接下来,定义一个getter函数以从对象中获取房间和消息。 invoker
是此snipet的核心部分,它返回一个调用方法的函数。见http://ramdajs.com/docs/#invoker
var getCurrentRoom = R.invoker(0, 'currentRoom')
var getMessages = R.invoker(0, 'messages')
以上代码可以如下使用。
var userWithRoom = withDefaults({
currentRoom : function () {
return {
number : '123'
}
}
})
var userWithMessages = withDefaults({
messages : function () {
return [
'get lunch'
]
}
})
var userWithAll = withDefaults({
currentRoom : function () {
return {
number : '123'
}
},
messages : function () {
return [
'get lunch'
]
}
})
var userWithNone = withDefaults({})
一起
var withDefaults = R.pipe(
R.unless(
R.hasIn('currentRoom'),
R.assoc('currentRoom',
R.always({}))),
R.unless(
R.hasIn('messages'),
R.assoc('messages',
R.always([]))))
var getCurrentRoom = R.invoker(0, 'currentRoom')
var getMessages = R.invoker(0, 'messages')
// examples
var userWithRoom = withDefaults({
currentRoom : function () {
return {
number : '123'
}
}
})
var userWithMessages = withDefaults({
messages : function () {
return [
'get lunch'
]
}
})
var userWithAll = withDefaults({
currentRoom : function () {
return {
number : '123'
}
},
messages : function () {
return [
'get lunch'
]
}
})
现在让我们使用console.log
测试上面的代码,看看我们的解决方案是否按预期工作
console.log(getCurrentRoom(userWithRoom))
console.log(getCurrentRoom(userWithMessages))
console.log(getCurrentRoom(userWithAll))
console.log(getCurrentRoom(userWithNone))
console.log('---')
console.log(getMessages(userWithRoom))
console.log(getMessages(userWithMessages))
console.log(getMessages(userWithAll))
console.log(getMessages(userWithNone))
输出应为:
{ number: '123' }
{}
{ number: '123' }
{}
---
[]
[ 'get lunch' ]
[ 'get lunch' ]
[]