简体   繁体   English

使用包装程序在Python / Javascript中模仿按引用传递-良好做法?

[英]Mimicking Pass-By-Reference in Python/Javascript Using Wrappers - Good Practice?

Say I want to modify a number or some other primitive inside of a function. 假设我要在函数内部修改数字或其他原始类型。 For example, something like this (note: pseudocode): 例如,如下所示(注意:伪代码):

// apply fn to every value in a tree, in-order traversal
function treeReduce (tree, fn, result):
    if (tree == undefined) return
    treeReduce(tree.left, fn, result)
    result = fn(result, tree.value)
    treeReduce(tree.right, fn, result)

sum = 0
treeReduce(myTree, +, sum)

obviously this won't work, because result is just being reassigned, and the sum passed in won't see the modifications. 显然,这是行不通的,因为只是重新分配了result ,并且传入的sum将看不到修改。 So a common way I have gotten around this (in any pass-by-value language like Python or Javascript) is using wrappers: 因此,我解决此问题的通用方法(在任何传递值的语言(如Python或Javascript)中都使用包装器:

// apply fn to every value in a tree, in-order traversal
function treeReduce (tree, fn, result):
    if (tree == undefined) return
    treeReduce(tree.left, fn, result)
    result[0] = fn(result[0], tree.value)
    treeReduce(tree.right, fn, result)

sumWrapper = [0]
treeReduce(myTree, +, sumWrapper)

However, I recently searched the internet to see if this is a common pattern, and can't find much information about it. 但是,我最近在互联网上搜索了这是否是一种常见模式,并且找不到太多有关此模式的信息。 Specifically, I'd like to know three things: 具体来说,我想知道三件事:

  1. is this a common pattern? 这是常见的模式吗?
  2. is this good practice? 这是好习惯吗?
  3. if not, any alternatives? 如果没有,还有其他选择吗?

It could be done like that, however it increases "sideeffects" of your function which most coders would advise to minimise as much as possible. 可以这样做,但是会增加函数的“副作用” ,大多数编码人员建议尽量减少这些副作用 Instead you could use the function's return value for it. 相反,您可以为其使用函数的返回值。 Your code would then still pass the "previous" (or "start") value as a primitive, but return the result. 然后,您的代码仍将传递“ previous”(或“ start”)值作为原语,但返回结果。

Here is how it would look in JS (I took a less trivial fn to demonstrate it performs an in-order execution): 这是在JS中的外观(我花了一些不小的琐碎的fn来演示它执行了有序执行):

 // apply fn to every value in a tree, in-order traversal function treeReduce (tree, fn, start) { if (tree === undefined) return start let result = treeReduce(tree.left, fn, start) result = fn(result, tree.value) result = treeReduce(tree.right, fn, result) return result } let myTree = { value: 1, left: { value: 2 }, right: { value: 3 } } let result = treeReduce(myTree, (a,b) => a*a+b, 0) console.log(result) 

Note that the above can be written more concisely now: 请注意,以上内容现在可以更简洁地编写:

 // apply fn to every value in a tree, in-order traversal function treeReduce (tree, fn, start) { return !tree ? start : treeReduce(tree.right, fn, fn(treeReduce(tree.left, fn, start), tree.value)) } let myTree = { value: 1, left: { value: 2 }, right: { value: 3 } } let result = treeReduce(myTree, (a,b) => a*a+b, 0) console.log(result) 

In Python: 在Python中:

import collections
Tree = collections.namedtuple('Tree', ['value', 'left', 'right'])

# apply fn to every value in a tree, in-order traversal
def treeReduce (tree, fn, start):
    return start if not tree else ( 
        treeReduce(tree.right, fn, fn(treeReduce(tree.left, fn, start), tree.value))
    )

myTree = Tree(1, Tree(2,None,None), Tree(3,None,None))

result = treeReduce(myTree, lambda a,b: a*a+b, 0)

print(result)

Both JS and Python also allow to extend this to the case where you would need to set multiple primitive values: functions can return arrays/lists/tuples/objects, which can then be assigned by unpacking/destructuring them into separate variables. JS和Python都允许将其扩展到需要设置多个原始值的情况:函数可以返回数组/列表/元组/对象,然后可以通过将它们解压缩/分解为单独的变量来进行赋值。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 通过引用传递 JavaScript 对象 - Pass-by-reference JavaScript objects JavaScript 是按引用传递还是按值传递语言? - Is JavaScript a pass-by-reference or pass-by-value language? JavaScript传递引用如何解释此行为? - How does JavaScript pass-by-reference explain this behavior? JavaScript中的按值传递和按引用传递有什么区别? - What's the difference between pass-by-value and pass-by-reference in JavaScript? 是否可以通过引用传递或访问实际对象? - Is it possible to pass-by-reference or access the actual object? JavaScript:创建未知维多维数组函数时的按引用传递问题 - JavaScript : Pass-by-reference issues when creating an unknown dimension multi dimensional array function 尝试在JavaScript中复制通过引用行为:如何适当地修改我的代码 - Trying to replicate pass-by-reference behavior in JavaScript: How to modify my code appropriately 在JavaScript中使用“耐用对象”是一种好习惯吗? - Is using of “Durable Object” a good practice in JavaScript? 从 javascript 中的参考文献中定义具有不同 arguments 列表的 function 是一种好习惯吗? - Is it good practice to define a function with different arguments list from reference in javascript? Javascript - 这是一个好习惯吗? - Javascript - Is this a good practice?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM