Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/delphi/8.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Delphi 是否有将圆的度数移过0的功能?_Delphi_Math_Geometry_Delphi Xe2 - Fatal编程技术网

Delphi 是否有将圆的度数移过0的功能?

Delphi 是否有将圆的度数移过0的功能?,delphi,math,geometry,delphi-xe2,Delphi,Math,Geometry,Delphi Xe2,我正在Delphi XE2中寻找一个类似于Inc()的函数,它允许我从当前度数中添加/减去度数,并生成新度数。例如,如果我有一个点当前围绕一个圆5度,我想减去10,我不应该得到-5度,而是355(360-5)。与添加过去的360相同-当它达到360时应返回到0 Delphi中已经有类似的东西了,这样我就不必重新编写了吗?也许在数学单元中?我什么都不知道,但我更喜欢使用更一般的解决方案 Procedure IncOverFlow(var Value:Double;Difference:Double

我正在Delphi XE2中寻找一个类似于
Inc()
的函数,它允许我从当前度数中添加/减去度数,并生成新度数。例如,如果我有一个点当前围绕一个圆5度,我想减去10,我不应该得到-5度,而是355(360-5)。与添加过去的360相同-当它达到360时应返回到0


Delphi中已经有类似的东西了,这样我就不必重新编写了吗?也许在
数学
单元中?

我什么都不知道,但我更喜欢使用更一般的解决方案

Procedure IncOverFlow(var Value:Double;Difference:Double;Limit:Double=360);
begin
   Value := Value + Difference;
   While Value < 0 do Value := Value + Limit;
   While Value >= Limit do Value := Value -Limit;
end;
程序入流(var值:双精度;差值:双精度;限值:双精度=360);
开始
值:=值+差;
当值<0时,do值:=值+极限;
而值>=限制do值:=值-限制;
结束;

我用于执行此任务的代码是:

function PosFrac(x: Double): Double;
(* PosFrac(1.2)=0.2 and PosFrac(-1.2)=0.8. *)
begin
  Result := Frac(x); (* Frac(x)=x-Int(x) *)
  if Result<0.0 then begin
    Result := 1.0+Result;
  end;
end;

function ModR(const x, y: Double): Double;
(* ModR(1.2,1)=0.2 and ModR(-1.2,1)=0.8 *)
var
  absy: Double;
begin
  if y=0.0 then begin
    Result := 0.0;
  end else begin
    absy := abs(y);
    Result := PosFrac(x/absy)*absy;
  end;
end;

function Mod360(const x: Double): Double;
begin
  Result := ModR(x, 360.0);
end;
产出:

355 5 5 5 355 5. 5. 5. 生成结果:

355
5 
0
更新:

正如@Giel所发现的,在XE3中有一个新函数
degmnormalize()
,它完成了这项工作。甚至快了25%。诀窍是将
Floor()
调用替换为
Int()
,如果结果为负,则将
modAngle
添加到结果中。

函数WrapAngle(值:Integer):Integer;
function WrapAngle(Value: Integer): Integer;
begin
  Result := Value mod 360;
  if Result < 0 then
    Inc(Result, 360);
end;
开始 结果:=值mod 360; 如果结果<0,则 公司(结果,360); 结束;
程序包装(var Degs:整数);
开始
Degs:=Degs mod 360;
如果Degs<0,则
公司(Degs,360),;
结束;

考虑到我最终使用的每个公式都需要弧度,我倾向于使用
DegToRad
RadToDeg
@Petesh help me,我看不出问题的上下文。有些API的使用度,表面上是正常的。我不是在敲你的答案;这对于基于浮点的通用增量函数非常有用。只是
RadToDeg(DegToRad(Value+Increment))
或多或少会给出相同的答案(+/-通常的转换错误)我在你第一次发布Showmessage(FloatToStr(radtodegtorad(350+70)))后尝试过这个;我得到的是420…@Marjan这个代码已经在OrcaFlex中运行了25年。这种不寻常的注释风格是因为代码从Modula-2开始就没有更改过!25年了?美好的甚至没有注意到评论风格。我经常使用
(**)
复制我正在使用的粘贴内容,将其与普通注释区分开来,并避免
{}
注释的不可嵌套性。谢谢,我在应用程序中经常使用它。通过将modAngle替换为2*Pi,您也可以使用弧度函数。或通过模数作为参数。我的版本似乎不必要的复杂。我想我们在其他例程中使用了一些助手。+1,并删除了我的。很好,还可以处理无效值。@Ken看一下您现在删除的答案的修订版1。我猜你发帖子的时候出了差错。我认为您最初发布的代码与生成输出时IDE中的代码不太一样。我的意思是Marjan没有破坏你的密码。她正试图修复它。但她甚至没有做到这一点。无论如何,LURD的答案显然是正确的。浮点数。接受任何范围的输入。大卫:谢谢。不确定代码发生了什么(显然是罪过)。我从来没有暗示过有人(特别是马扬)打破了任何东西;我只是想指出,我实际上测试了代码。好像我把事情搞得不同步了。(这一点有点没有实际意义,因为我在今天早上编辑后很快就删除了答案。):-)记录如下:Delphi XE3在System.Math中确实有一个DegNormalize()函数。我想评论一下,这个问题、答案和注释概括了我为什么喜欢堆栈溢出。我已经学到了很多关于一个小功能的知识,我认为我已经学好了。大家都玩得很好!所有这些知识都锁在开发人员的头脑和代码中,我们不知道我们不知道什么。。。这就是扩展我们专业知识的妙处。这可能是整数输入最简洁的方法。
355
5 
0
function WrapAngle(Value: Integer): Integer;
begin
  Result := Value mod 360;
  if Result < 0 then
    Inc(Result, 360);
end;
procedure WrapAngle(var Degs: Integer);
begin
  Degs := Degs mod 360;
  if Degs < 0 then
    Inc(Degs, 360);
end;