尝试使函数通用,但陷入困境

发布于 2024-10-11 14:37:56 字数 1336 浏览 7 评论 0原文

我在包中有一个变量(在本例中为 rec),在从 package 3 调用时需要设置该变量,但它是私有的。以前,函数 set_true 仅将 rec 设置为 true,因此这没什么大不了的。但是我有另一个包可以进行相同的处理(我给出了一个简单的例子,但我的字面情况更复杂),所以我想,我可以传入我想要修改的变量,并让它改变。是在下面的布局中设置 rec 的唯一方法,以便在包一中创建第二个函数,该函数以 rec 作为参数调用 set_true ?我想避免必须不断创建额外的函数来处理局部变量。我无法将变量移至公共(规范),因为我试图遵循约定,并且这种“类型”变量在其他任何地方都不是公共的,而且我不希望任何人能够自己设置它(我希望必须设置功能)。我不想创建第二个名为 set_local_true 的函数,并创建一个不带参数的重载函数 set_true,该函数调用 set_true(value =>rec) 只是看起来具有欺骗性,有人对我的限制有更好的建议吗?

我的两个要求:

  1. 不能将局部变量公开。
  2. 能够使用该函数进行外部和内部计算。
package one is
   procedure set_true(value : out Boolean);
end one;

package body one is
   rec : Boolean;
begin
   procedure set_true(value : out Boolean)
   begin
      value := true;
   end set_true;
end one;

package body two is
   local_rec : Boolean;
begin
   procedure call_function is
   begin
      one.set_true(value => local_rec);
   end call_function;
end two;

package body three is
begin
   procedure call_function is
   begin
      one.set_true(value => <PACKAGE ONE'S REC))
   end call_function;
end three;

编辑:或者也许,对于函数来说,更好的命名约定是什么来指定它们正在修改该包本地的变量? Set_Local_True 再次是欺骗性的,因为如果您从包 3 调用它,则您没有将本地设置为 true,而是将包的本地设置为 true....

I have a variable in a package (rec in this case) that needs to be set when called from package 3, but it's private. Previously the function set_true only set rec to true, so it wasn't a big deal. But I have another package that does the same processing (I'm giving a simple example, but my literal case is more complex), so I thought, well I could pass in the variable I want modified, and let it get changed. Is the only way to set rec in the below layout, to create a second function in package one, that calls set_true with rec as the parameter? I would like to avoid having to keep creating additional functions to handle the local variables. I can't move the variable to public (spec) as I am trying to follow convention and this "type" of variable isn't public anywhere else, and I don't want anyone to be able to just set it on their own (I want functions to have to set). I don't want to have to create a second function named for example set_local_true, and creating an overloaded function set_true, with no parameters, that calls set_true(value => rec) just seems deceptive, does anyone have any better suggestions with the limitations I have?

My two requirements:

  1. Can't make the local variable public.
  2. Be able to use the function to calculate something both externally and internally.
package one is
   procedure set_true(value : out Boolean);
end one;

package body one is
   rec : Boolean;
begin
   procedure set_true(value : out Boolean)
   begin
      value := true;
   end set_true;
end one;

package body two is
   local_rec : Boolean;
begin
   procedure call_function is
   begin
      one.set_true(value => local_rec);
   end call_function;
end two;

package body three is
begin
   procedure call_function is
   begin
      one.set_true(value => <PACKAGE ONE'S REC))
   end call_function;
end three;

EDIT: Or perhaps, what would be a better naming convention for the functions to specify that they are modifying the variable that is local to that package? Set_Local_True again is deceptive cause if you call it from package 3, you're not setting your local true, you're setting package one's local to true....

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

旧城烟雨 2024-10-18 14:37:56

首先,这是非常愚蠢的代码。我假设它是其他东西的简写。但正如所介绍的,我可以向您保证,您的客户可以自己设置自己的布尔值,而无需您编写例程来为他们执行此操作。事实上,他们可以做得更好。对于这个答案的其余部分,我假设您实际上并没有编写变量来为人们设置布尔值,而是做一些实际使用的事情。如果没有,请忽略此答案的其余部分,并删除您愚蠢的例程。

其次,如果您正在创建一个带有单个输出参数的例程,那么除非该对象恰好非常大,否则您应该将其改为函数。如果您的客户选择的话,这将允许他们使用函数式编程。按照您的方式,可怜的编码员必须停下来并创建一个特殊变量来调用您的例程,即使他们只想执行一次。

第三,我通常更喜欢传递请求的状态,而不是为每个状态使用唯一的设置例程。

function Set_Frobnost (New_State : boolean := true) return boolean;

如果状态确实是布尔值(将来不可能有第三种状态),那么它是有争议的。但是,如果您的客户可能已经必须将状态存储在变量中(或循环遍历它),那么这对您的客户来说可能是一个很大的优势。

您对命名的编辑表明您走在正确的道路上。

您应该在这里做两件事之一。

  1. 找到由该变量控制的更高级别的概念,并在其后命名“setter”例程。
  2. 赶紧让开,把 flag 变量放到 pacakge 规范中。

First off, this is very silly code. I'll assume it is shorthand for something else. But as presented, I can assure you that your clients can set their own booleans themselves without you writing a routine to do it for them. In fact, they can do it better. For the remainder of this answer, I'll assume you aren't acutally writing variables to set booleans for people, but rather doing something of actual use. If not, ignore the rest of this answer and just delete your silly routines.

Secondly, if you are creating a routine with a single out parameter, then unless the object happens to be very large, you should probably make it a function instead. That will allow your clients to use functional programming if they chose. The way you have it, the poor coder has to stop and create a special variable just to call your routine, even if they only want to do it once.

Thirdly, rather than using a unique set routine for each state, I generally prefer to pass in the requested state.

function Set_Frobnost (New_State : boolean := true) return boolean;

If the state is really and truly boolean (no possible third state in the future), then it is debateable. However, it can be a big advantage to your client if they might already have to store the state in a variable (or loop through it).

Your edit about naming shows me you are on the right track.

You should do one of two things here.

  1. Find the higher-level concept controlled by that variable, and name the "setter" routine after that.
  2. Get the hell out of the way and put the flag variable in the pacakge spec.
香橙ぽ 2024-10-18 14:37:56

如果您必须访问私有变量,您可能会在子包中执行此操作。

package One is
   procedure Foo (X : Boolean);
private
   One_Private : Boolean;
end One;

然后

package body One.Two is
    procedure Bar is
       One.Foo (One.One_Private);
    end Bar;
end One.Two;

包的“私有”部分中的元素就像 C++/Java 中的“受保护”实体。真正的私有变量(仅在包体中)无法从其他任何地方访问。

If you have to access private variables, you might to do it in a child package.

package One is
   procedure Foo (X : Boolean);
private
   One_Private : Boolean;
end One;

and then

package body One.Two is
    procedure Bar is
       One.Foo (One.One_Private);
    end Bar;
end One.Two;

Elements in the "private" part of a package are like "protected" entities in C++/Java. Truly private variables (only in package body) are not accessible from anywhere else.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文