0

寻找有关此代码的一些帮助。如果不发布太大的整个文件,我只需要在 Coldfusion 中使用 Nullif 的一些帮助。

我猜我可以在我的 SQL 语句中使用它,但为了学习,我想知道在设置变量时是否可以使用它:-

该代码不会引发任何错误,但我想知道在 Nullif 之后将 0 放在哪里。

<cfif AE_C NEQ 0>
    <cfset AE_P=AE_T/AE_C>
    <cfset AE_A=AE/AE_C*100>
    <cfset AE_B = AE-AE_C/H8*H9>
    <cfset AE_D=AE/H9*H8> 
<cfelse>
    <cfset AE_P=ISNULL(AE_T/NULLIF(AE_C))>
    <cfset AE_A=ISNULL(AE/NULLIF(AE_C*100))>
    <cfset AE_B=ISNULL(AE-AE_C/NULLIF(H8*H9))>
    <cfset AE_D=ISNULL(AE/NULLIF(H9*H8))>
</cfif>

希望可以通过这种方式实现。

4

3 回答 3

1

这是由 Ben Nadel 编写的一些代码,我发现它可以解决错误,也许有人可以帮助我如何实现它,因为我无法理解它。

<!---
Do SQL division with divide-by-zero protection. But this,
time, let's provide a default value if the division is
not valid.
--->
<cfquery name="qDivision" datasource="#REQUEST.DSN.Source#">
SELECT
    (
        ISNULL(
            (45 / NULLIF( 0, 0 )),
            0
        )
    ) AS value
  ;
</cfquery>

<!--- Output resulting value. --->
[ #qDivision.value# ]
于 2018-08-04T02:15:44.667 回答
1

重要提示:您的代码没有显示任何错误,因为ISNULL它掩盖了错误。


也不NULLIF是有效的 ColdFusion 功能。我相信您的页面没有错误的原因是,ColdFusionISNULL()功能似乎是一种非常通用的功能,并且显示出一些未记录的特征。ISNULL()如果表达式在语法上有效,即使其中的表达式已定义或未定义,也不会返回错误。

例如。

ISNULL(AE_T/NULLIF(AE_C)) // No error because AE_T/NULLIF(AE_C) is a valid statement.

作为替代方案,您可以执行以下操作。

以下有点hacky,但您可以查看该功能val()。对于任何不是数字的字符串,它将返回 0(有关更多详细信息,请查看文档)。

NULLIF(AE_C)变成val(AE_C).

<cfset AE_P=ISNULL(AE_T/val(AE_C))>

仍然如果val()返回0,那么的输出ISNULL()将会是YES,因为除以0抛出错误。

于 2018-08-03T11:56:00.373 回答
0

这更像是一个评论而不是一个答案。请参阅 RRK 关于NULLIF不是有效的 ColdFusion 功能和ISNULL()隐藏错误的答案。

我的评论更多的是关于您的操作逻辑。您不需要执行您的某些步骤<CFELSE>

原来的:

<cfif AE_C NEQ 0>
    <cfset AE_P=AE_T/AE_C>
    <cfset AE_A=AE/AE_C*100>
    <cfset AE_B = AE-AE_C/H8*H9>
    <cfset AE_D=AE/H9*H8> 
<cfelse>
    <cfset AE_P=ISNULL(AE_T/NULLIF(AE_C))>
    <cfset AE_A=ISNULL(AE/NULLIF(AE_C*100))>
    <cfset AE_B=ISNULL(AE-AE_C/NULLIF(H8*H9))>
    <cfset AE_D=ISNULL(AE/NULLIF(H9*H8))>
</cfif>

我假设您正在使用NULLIF()来防止divide by zero错误。

首先,在我熟悉的语言中,NULLIF()需要两个参数:NULLIF(a,b)如果a不等于b,则返回a,否则返回NULL

也就是说,你cfif说如果AE_C不是0那么做x,否则做y。我假设它应该是<cfset AE_P=ISNULL(AE_T/NULLIF(AE_C,0))>。如果你推断出来,你会得到AE_T/NULLIF(0,0)== AE_T/NULL== NULL。因此,您可以将该块短路并设置AE_P=NULL. 但是你也有ISNULL()围绕它的功能,所以这也总是正确的。并且ISNULL()(在 ColdFusion 中除外)也需要 2 个参数。在 CF 中,它返回TRUE/ FALSE(或YES/NO是迂腐的)。所以现在你基本上已经完成了<cfset AE_P = YES/TRUE>。我猜这不是你的初衷。所以ISNULL()这里可能不合适。在 SQL 中,ISNULL(a,b)这意味着 if ais NULL, return b。所以(在 ​​SQL 中)你基本上可以做AE_P = ISNULL(x,0)这意味着如果AE_C0,而不是得到divide by zero错误,你可以设置AE_P = 0

TLDR;ColdFusion中没有NULLIF()函数,因此如果您想防止div0错误,您必须在 SQL 中执行此操作或修改您的 ColdFusion 集:

<cfif AE_C NEQ 0>
    <cfset AE_P=AE_T/AE_C>
    <cfset AE_A=AE/AE_C*100>
<cfelse>
    <cfset AE_P=0>
    <cfset AE_A=0>
</cfif>

我不知道您的代码流程,所以我不知道如何H8以及H9受其影响AE_C,因此您可能还需要检查这些0

但是,我仍然会回到我通常的信念,如果这些计算是在 SQL 中使用而不是在代码中使用,那么它们应该在 SQL 中完成,而不是传递给应用服务器,然后再传回 SQL。不过,我不知道您的代码在做什么,因此在代码中包含这些计算可能更合适。

于 2018-08-03T15:08:57.863 回答