首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >管内层流的速度分布

管内层流的速度分布
EN

Code Review用户
提问于 2017-11-29 18:47:27
回答 1查看 856关注 0票数 2

对于一个大学项目,我想要计算管道横截面上7点的层流速度。稍后,我们希望将这些数据用于流动画。

我函数的输入是管道的直径和长度,流体的粘度,压差和平均速度。

对于计算,我只需要压差或平均速度。所以我必须把压差或者平均速度设定为假。

你知道我怎样才能改进代码吗?

代码语言:javascript
运行
复制
import numpy as np


def flow(diameter, viscosity, len_pipe, dp, v_average):
    radius = diameter / 2.
    x = np.linspace(-radius, radius, 7)

    if not v_average and dp:
        dpdx = dp / float(len_pipe)
        v = radius**2 / (4*viscosity) * (-dpdx) * (1-(x/radius)**2)
        vmax = max(v)
        v_average = vmax / 2
    elif not dp and v_average:
        vmax = 2 * v_average
        dpdx = -4 * vmax * viscosity / radius**2
        dp = dpdx * len_pipe
        v = radius**2 / (4*viscosity) * (-dpdx) * (1-(x/radius)**2)

    return dp, v_average, x, v, vmax
EN

回答 1

Code Review用户

发布于 2017-11-30 00:00:01

我首先要说的是,我几乎同意@ConorMancone的评论中的所有内容。先读一下。这么说..。

检查你的数学

我对层流一无所知。所以我在维基百科上查了一下,我不认识你用的方程式。也许你有一种特殊的限制形式。或者你所使用的东西比在WP上显示的东西更先进或者更基本。或者我只是跳过了包含你方程的那一节--这并不是我花了大量的时间去寻找。

无论如何,您应该检查您的数学实际上是有效的-忽略了整个“在python中实现”部分。

一旦您确定您的数学是正确的,请将方程及其公式的名称放在函数开头的docblock注释中:

代码语言:javascript
运行
复制
def flow(...):
    """Compute the laminar flow through a pipe of constant diameter
    using Professor Farnsworth's equation:

        flow = eˣ dy/dx eʸ dy sec(tan(cos(sin(3.14159))) √ ∛ ln e 
        # circular slide rule, CIT!

    """

确定并使用“正式”形式的方程式-而不是一个副本的任何源代码。理想情况下,在注释中使用unicode字符,将数学所需的希腊字母、奇异符号等放入其中。如果可能的话,它应该像你的参考文本。

这样做的目的是提供理想表单的副本,这样您可以在编码时查找并检查它。

改进您的签名

正如Conor所指出的,您的函数签名不是很好。当我编码以下代码时,这意味着什么:

代码语言:javascript
运行
复制
flow(3.1, 2, 7, 15)

可以通过使用变量命名参数来克服其中的一些问题:

代码语言:javascript
运行
复制
flow(diameter, viscosity, length, 15)

但是,更好的方法是在功能定义中使用命名参数或仅命名参数,以便调用者列出部分或全部参数名称:

代码语言:javascript
运行
复制
def flow(*, diameter, length, viscosity, velocity=None, delta_p=None):
    pass

使用有意义的参数名

根据维基百科的说法,希腊字母mu (μ)常用于粘度。因此,也许使用muμ作为您的参数名是有意义的。(也许不是:除非你的源代码读者理解它,否则它并不是不言自明的。)

显式优于隐式

你在测试你的输入时做得很糟糕。事实上,有两个bug:

代码语言:javascript
运行
复制
if not v_average and dp:
    ...

elif not dp and v_average:
    ...

return dp, v_average, x, v, vmax

首先,问问自己:我的条件是否构成了可能的输入值的完整分区?在这种情况下,没有。还有另外两种可能的输入条件:not dp and not v_averagedp and v_average

dp and v_average的情况下,您要做的就是选择一个分支并执行它!在输入值都不匹配的情况下,需要引发异常或提供一些默认值或其他东西。

更糟糕的是,考虑到整数0是错误的。也就是说,当您有一个值x=None,并且您说if x:时,它将被计算为一个不正确的状态。当你有一个值x=0,你说if x:,它也将被评估为一种虚假的状态。

这意味着,例如,如果有人要动态计算dp,比如:

代码语言:javascript
运行
复制
f = flow(diameter=10, mu=1.2, length=33, dp=abs(p[0] - p[-1]))

dp有可能被计算为零。在这种情况下,您的情况将失败,因为它检查dp。相反,您应该显式地测试None,并确保如果输入dp=0,您的数学就能存活下来:

代码语言:javascript
运行
复制
if dp is None:
    # No dp provided
票数 4
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/181604

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档