From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00 autolearn=ham autolearn_force=no version=3.4.4 X-Google-Thread: 103376,e01fe1b326df26d4 X-Google-Attributes: gid103376,public X-Google-Language: ENGLISH,ASCII-7-bit Path: g2news1.google.com!news4.google.com!news.glorb.com!news.mv.net!nntp.TheWorld.com!not-for-mail From: Robert A Duff Newsgroups: comp.lang.ada Subject: Re: Division by zero Date: 13 Jun 2005 08:19:59 -0400 Organization: The World Public Access UNIX, Brookline, MA Message-ID: References: <79ahr0jozmqb$.10jzllrcjpmsv.dlg@40tude.net> NNTP-Posting-Host: shell01.theworld.com Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Trace: pcls4.std.com 1118665199 31752 192.74.137.71 (13 Jun 2005 12:19:59 GMT) X-Complaints-To: abuse@TheWorld.com NNTP-Posting-Date: Mon, 13 Jun 2005 12:19:59 +0000 (UTC) User-Agent: Gnus/5.09 (Gnus v5.9.0) Emacs/21.2 Xref: g2news1.google.com comp.lang.ada:11319 Date: 2005-06-13T08:19:59-04:00 List-Id: Jeffrey Carter writes: > Robert A Duff wrote: > > Well, in Ada 83, the "class of errors" was "divide by zero". > > In Ada 95, that was split into "divide by zero in a static expression" > > and "divide by zero in a nonstatic expression" -- the former is a > > compile time error, whereas the latter is a run-time error. > > There's nothing illogical about splitting it further: > > "divide by zero when the Right operand is static" could be defined > > as a compile-time error. The problem is that if you try to define > > all the compile-time-detectable cases very precisely, it gets quite > > complicated. And however you define it, it *has* to be conservative. > > The problem, it seems to me, is that the developer may deliberately > write a division of a variable by static zero for a number of > reasons. He may want it to raise Constraint_Error at run time,... It's hard to come up with legitimate examples of that. As others have pointed out, "raise C_E" is usually the best way to raise C_E. Here's an example that agrees with your point: Suppose I have a constant Widgets that is different on different operating systems. So I create two versions of the same package, and the Windows version says "Widgets: constant Integer := 23;" and the Unix version says "Widgets: constant Integer := 0;". I have some configuration scripts to pick the right version of the source code to compile. (This is a common way of dealing with OS dependencies.) Now I have a variable Gizmos, and I want to print out the numbers of Gizmos per Widget (when that's meaningful). In *portable* code, I might want to write: if Widgets = 0 then Put_Line("Unknown"); else Put_Line(Image(Gizmos/Widgets)); end if; If divide by zero were illegal at compile time, even in unreachable code, the above would be annoying illegal on Unix. So I would have to move the above if statement into the OS-specific files, thus increasing their size -- a Bad Thing. Or, I would have to make Widgets nonstatic, which might be damaging for other reasons. (In fact, if Gizmos is static, then the above *is* illegal in Ada 95, but not Ada 83.) Can anybody think of a better example (i.e. one that does not involve extra-lingual features such as OS-specific source code versions)? >... or may > have redefined "/" for the type of the variable to do something > meaningful if the divisor is zero. The rules about static expressions do not apply to user-defined operators, which can do anything you like. > This latter case invalidates an earlier example. The following should > compile and output Integer'Last before terminating normally: > > with Ada.Text_IO; > procedure Zero_Div is > function "/" (Left : Integer; Right : Integer) return Integer is > -- null; > begin -- "/" > if Right = 0 then > return Integer'Last; > else > return Left / Right; Careful! That looks like an infinite recursion. You need to do some horsing around to get at the predefined "/", so you can call it from the user-defined one. > end if; > end "/"; > > A : constant Integer := 23; > B : constant Integer := 0; > begin -- Zero_Div > Ada.Text_IO.Put_Line (Item => Integer'Image (A / B) ); > end Zero_Div; - Bob