gpt4 book ai didi

postgresql - plpgsql 中 WHILE 循环的 "END LOOP;"部分出现语法错误

转载 作者:行者123 更新时间:2023-11-29 12:41:06 25 4
gpt4 key购买 nike

尝试在 plpgsql 中定义一个我无法解释的函数时出现语法错误。出于某种原因,这段代码总是会失败,并出现 语法错误 at or nor "LOOP":

CREATE OR REPLACE FUNCTION ST_Dilate(
in_geom GEOMETRY,
scale_factor FLOAT,
tol FLOAT DEFAULT 0.001,
guess FLOAT DEFAULT 1,
safety INTEGER DEFAULT 1000
)

RETURNS GEOMETRY AS

$$
DECLARE
step FLOAT = guess/2;
current_area FLOAT = ST_Area(ST_Buffer(in_geom, buff));
desired_area FLOAT = ST_Area(in_geom)*scale_factor;
dev FLOAT = (current_area-desired_area)/desired_area;
old_dev FLOAT;
safety_counter INTEGER = 0;
BEGIN

WHILE ABS(dev) > tol LOOP

IF safety_counter > safety THEN /* Can't find suitable distance after many iterations, terminate the function to prevent extreme hangs. */
RAISE NOTICE 'Could not find suitable buffer distance when dilating geom % after % iterations, NULL geometry returned instead. Consider adjusting "guess" parameter value or initial step size.', geom, safety;
RETURN NULL;
END IF;
safety_counter = safety_counter + 1;

/* Save the old deviation to be compared later to the new one later, calculate the current area and the new deviation from the desired area. */
old_dev = dev;
current_area = ST_Area(ST_Buffer(in_geom, guess));
dev = (current_area - desired_area) / desired_area;

IF dev < 0 THEN /* Current area is smaller than desired area, increase the buffer distance by the step. */
guess = guess + step;
ELSE IF dev > 0 THEN /* Current area is larger than desired area, decrease the buffer distance by the step. */
guess = guess - step;
ELSE /* Technically shouldn't ever happen because then ABS(dev) is indeed lesser than tol but here just in case. */
EXIT;
END IF;

IF dev * old_dev < 0 THEN /* Negative value indicates difference of sign, which means we just overestimated the area after underestimating it or vice versa, need to half the step. */
step = step * 0.5;
END IF;

END LOOP; /* syntax error here */

RETURN ST_Buffer(in_geom, guess);

END
$$
LANGUAGE plpgsql;

我根本没有看到语法错误。更令人困惑的是,如果我注释掉这个 block :

IF safety_counter > safety THEN /* Can't find suitable distance after many iterations, terminate the function to prevent extreme hangs. */
RAISE NOTICE 'Could not find suitable buffer distance when dilating geom % after % iterations, NULL geometry returned instead. Consider adjusting "guess" parameter value or initial step size.', geom, safety;
RETURN NULL;
END IF;
safety_counter = safety_counter + 1;

代码成功执行一次,但第二次立即失败并出现相同的错误。

我对此完全感到困惑。我一次一个地注释掉了每个 block 以及试图找到问题的各个行,但我在任何地方都找不到语法错误,但它一直在提示。

我在 postgresql 9.6 上。

最佳答案

如果你想获得单个 IF 语句,请使用 ELSIF:

    IF dev < 0 THEN /* Current area is smaller than desired area, increase the buffer distance by the step. */
guess = guess + step;
ELSIF dev > 0 THEN /* Current area is larger than desired area, decrease the buffer distance by the step. */
guess = guess - step;
ELSE /* Technically shouldn't ever happen because then ABS(dev) is indeed lesser than tol but here just in case. */
EXIT;
END IF;

阅读有关 Control Structures. 的文档

关于postgresql - plpgsql 中 WHILE 循环的 "END LOOP;"部分出现语法错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49883629/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com