digitalmars.D.learn - Question on nothrow
- Vasileios Anagnostopoulos (9/9) May 31 2017 Hi,
- Mike Parker (17/26) May 31 2017 This has come up several times over the years. For summary, go to
- Vasileios Anagnostopoulos (3/6) May 31 2017 Do you realize that I do not talk about checked exceptions, only
- =?UTF-8?Q?Ali_=c3=87ehreli?= (7/8) May 31 2017 For that to be possible, the compiler would have to see all definitions,...
- Vasileios Anagnostopoulos (5/14) Jun 01 2017 So the biggest question is, how do I know that a function "may
- =?UTF-8?Q?Ali_=c3=87ehreli?= (24/27) Jun 01 2017 I come from a C++ background so the advices may be different from Java's...
- Vasileios Anagnostopoulos (28/47) Jun 01 2017 Let us emulate this as function calls with void
- =?UTF-8?Q?Ali_=c3=87ehreli?= (17/25) Jun 01 2017 (Sorry if I go to too basic levels here.) I used to think that an
- Vasileios Anagnostopoulos (31/63) Jun 02 2017 But still I believe that @nothrow should be mandatory if there is
- Vasileios Anagnostopoulos (16/48) Jun 02 2017 Or simply
- =?UTF-8?Q?Ali_=c3=87ehreli?= (9/31) Jul 05 2017 If I understand you correctly, you want the compiler to force the
- Jonathan M Davis via Digitalmars-d-learn (22/31) May 31 2017 Well, if you're not doing checked exceptions, the interesting question i...
- Vasileios Anagnostopoulos (2/3) May 31 2017 Thank you for the answers.
- Yuxuan Shui (3/11) Jul 05 2017 I don't think this is possible in current D? @nothrow functions
- Yuxuan Shui (4/13) Jul 05 2017 Adding @throws to a function requires changing all the functions
Hi, after reading various articles bout the "supposed" drawbacks of checked exceptions I started to have questions on nothrow. Why there exists and not a throws annotation enforced by the compiler? I understand that people are divided on checked exceptions and each side has some valid points. But explicitly marking a function as throwing "something" is another subject. Why have the dlang community reached to the decision to use nothrow and not a throws?
May 31 2017
On Wednesday, 31 May 2017 at 08:18:07 UTC, Vasileios Anagnostopoulos wrote:Hi, after reading various articles bout the "supposed" drawbacks of checked exceptions I started to have questions on nothrow. Why there exists and not a throws annotation enforced by the compiler? I understand that people are divided on checked exceptions and each side has some valid points. But explicitly marking a function as throwing "something" is another subject. Why have the dlang community reached to the decision to use nothrow and not a throws?This has come up several times over the years. For summary, go to the search bar and type: "checked exceptions" Walter This will lead you to a number of choice quotes from Walter on the topic. Examples: "C++98 had checked exceptions (exception specifications), too. Another failure of the idea, it failed so badly hardly anyone but language lawyers ever knew it had it." "Checked exceptions is another feature that looks great on paper; it's only after years of use one discovers what a perniciously bad feature it is." I didn't go further, but there are probably some with more detail if you dig, and comments from several others on both sides. There's also this article he linked: http://www.mindview.net/Etc/Discussions/CheckedExceptions
May 31 2017
On Wednesday, 31 May 2017 at 08:52:51 UTC, Mike Parker wrote:This has come up several times over the years. For summary, go to the search bar and type: "checked exceptions" WalterDo you realize that I do not talk about checked exceptions, only a compiler enforced throws and nothing else?
May 31 2017
On 05/31/2017 02:10 AM, Vasileios Anagnostopoulos wrote:compiler enforced throwsFor that to be possible, the compiler would have to see all definitions, which is not possible with separate compilation. Besides, I think the only meaning of throws would be "may throw". If so, since the implementation of every function can be changed to call any other function, the possibility of throwing would always exist. Ali
May 31 2017
On Wednesday, 31 May 2017 at 17:20:08 UTC, Ali Çehreli wrote:On 05/31/2017 02:10 AM, Vasileios Anagnostopoulos wrote:So the biggest question is, how do I know that a function "may throw" an exception in order to use a try/catch/finally block? This is my biggest problem (sorry, coming from a java/C background).compiler enforced throwsFor that to be possible, the compiler would have to see all definitions, which is not possible with separate compilation. Besides, I think the only meaning of throws would be "may throw". If so, since the implementation of every function can be changed to call any other function, the possibility of throwing would always exist. Ali
Jun 01 2017
On 06/01/2017 06:26 AM, Vasileios Anagnostopoulos wrote:how do I know that a function "may throw" an exception in order to use a try/catch/finally block? This is my biggest problem (sorry, coming from a java/C background).I come from a C++ background so the advices may be different from Java's. The liberating thing about exceptions is that you simply do not catch them. In fact, you're adviced against catching them unless you want to or can do something when they are thrown. If you think that way, you write your code to do its resource management automatically with destructors, scope statements (scope(exit), scope(exception), and scope(success)), etc. Say, you want to send a letter by performing certain steps: grab a paper, write the letter, grab an envelope, put the letter inside, oops, there is no stamp. Throw an exception... If such low or intermediate level functions have no idea what the higher layer application code wants to do in this case, they simply throw. N layer up, a function would want to catch an Exception, log "failed to send to Ali because no stamp." So, nobody cared in this example who could throw. They simply did their tasks. Of course, it's not always as simple in practice but you almost never need to catch exceptions from individual functions. To contrast, C's error handling is too cumbersome as every single programming step must at least be two lines: first do it and then check the error code. (Go famously claims that it followed C in this regard for simplicity. Since they made other claims and have shown ignorance especially at the time of Go's introduction, I will never believe Go adopted C's error handling for simplicity.) Ali
Jun 01 2017
On Thursday, 1 June 2017 at 15:17:32 UTC, Ali Çehreli wrote:On 06/01/2017 06:26 AM, Vasileios Anagnostopoulos wrote:Let us emulate this as function calls with void void sendEmailToAli() { grabAPaper(); writeALetter(); grabAnEnvelope(); putTimeStamp(); //throws an Exception, function not in my control, residing in a dll putToMailBox(); }how do I know that a function "may throw" an exception in order to use a try/catch/finally block? This ismy biggestproblem (sorry, coming from a java/C background).I come from a C++ background so the advices may be different from Java's. The liberating thing about exceptions is that you simply do not catch them. In fact, you're adviced against catching them unless you want to or can do something when they are thrown. If you think that way, you write your code to do its resource management automatically with destructors, scope statements (scope(exit), scope(exception), and scope(success)), etc. Say, you want to send a letter by performing certain steps: grab a paper, write the letter, grab an envelope, put theletter inside, oops, there is no stamp. Throw an exception... If such low or intermediate level functions have no idea what the higher layer application code wants to do in this case, they simply throw. N layer up, a function would want to catch//If I knew about the exception //I could recover, because exceptions //signal recoverable errors void haveToCommunicateWithAli() { try { sendEmailToAli(); } catch(Exception e) { goPersonallyToAli(); } } //If I do not know void haveToCommunicateWithAli() { sendEmailToAli(); } //can blow-up after code has shipped //and have no chance to recover What shall I do in this case? Thank you in advance. Vasileios
Jun 01 2017
On 06/01/2017 08:41 AM, Vasileios Anagnostopoulos wrote://If I do not know void haveToCommunicateWithAli() { sendEmailToAli(); } //can blow-up after code has shipped //and have no chance to recover What shall I do in this case? Thank you in advance. Vasileios(Sorry if I go to too basic levels here.) I used to think that an unhandled exception was a program crash. It's not. It's a good thing that a program aborts due to an uhandled exception. What happened is that it could not achieve it's task. There was nothing else it could do, so it terminated. (For example, it did not continue with unhealthy radiation levels on the patient.) Although an abort may be the safest thing to do in many cases, it's not user-friendly. So, you catch the exception at the highest level that it matters or that you can do something about it. For example, you can catch the exception in main(), report a friendly error, and return 1. Or, you may be in a loop, preparing letters, you catch around that code and either report an error or perhaps grab more stamps and repeat the last operation. So the answer is, don't catch exceptions any lower than it really matters, which could be as high as the main() function. Ali
Jun 01 2017
On Thursday, 1 June 2017 at 17:03:52 UTC, Ali Çehreli wrote:On 06/01/2017 08:41 AM, Vasileios Anagnostopoulos wrote:But still I believe that nothrow should be mandatory if there is no possibility for a function to throw something. I understand that in the DLL/LIB level this is not possible. However, at least in the .di level it should be there. And if you want my two cents, after reading a lot I came to the "personal" conclusion that Exception objects are wrong. For me it is enough to have something like void A() { raise; } void B() { raise; } void C() { raise; } void D () nothrow { //the compiler inferred from body that D cannever throw scope(failure) { writeln("The end of the world"); exit(1); } try { A(); } else try { B(); } else { C(); } }//If I do not know void haveToCommunicateWithAli() { sendEmailToAli(); } //can blow-up after code has shipped //and have no chance to recover What shall I do in this case? Thank you in advance. Vasileios(Sorry if I go to too basic levels here.) I used to think that an unhandled exception was a program crash. It's not. It's a good thing that a program aborts due to an uhandled exception. What happened is that it could not achieve it's task. There was nothing else it could do, so it terminated. (For example, it did not continue with unhealthy radiation levels on the patient.) Although an abort may be the safest thing to do in many cases, it's not user-friendly. So, you catch the exception at the highest level that it matters or that you can do something about it. For example, you can catch the exception in main(), report a friendly error, and return 1. Or, you may be in a loop, preparing letters, you catch around that code and either report an error or perhaps grab more stamps and repeat the last operation. So the answer is, don't catch exceptions any lower than it really matters, which could be as high as the main() function. Ali
Jun 02 2017
On Friday, 2 June 2017 at 07:33:05 UTC, Vasileios Anagnostopoulos wrote:On Thursday, 1 June 2017 at 17:03:52 UTC, Ali Çehreli wrote:Or simply void A() { raise; } void B() nothrow { } void D () nothrow { //the compiler inferred from body that D cannever throw try { A(); } else { B(); } }[...]But still I believe that nothrow should be mandatory if there is no possibility for a function to throw something. I understand that in the DLL/LIB level this is not possible. However, at least in the .di level it should be there. And if you want my two cents, after reading a lot I came to the "personal" conclusion that Exception objects are wrong. For me it is enough to have something like void A() { raise; } void B() { raise; } void C() { raise; } void D () nothrow { //the compiler inferred from body that D cannever throw scope(failure) { writeln("The end of the world"); exit(1); } try { A(); } else try { B(); } else { C(); } }
Jun 02 2017
On 06/02/2017 12:35 AM, Vasileios Anagnostopoulos wrote:On Friday, 2 June 2017 at 07:33:05 UTC, Vasileios Anagnostopoulos wrote:But still I believe that nothrow should be mandatory if there is no possibility for a function to throw something. I understand that in the DLL/LIB level this is not possible. However, at least in the .di level it should be there. And if you want my two cents, after reading a lot I came to the "personal" conclusion that Exception objects are wrong. For me it is enough to have something likeOr simply void A() { raise; } void B() nothrow { } void D () nothrow { //the compiler inferred from body that D canneverthrowtry { A(); } else { B(); } }If I understand you correctly, you want the compiler to force the programmer to be explicit about nothrow. That's an interesting idea... I don't have strong opinions on the matter. To add to this discussion, there is the "Checked vs unchecked exceptions" thread currently active on the general newsgroup: http://forum.dlang.org/post/hxhjcchsulqejwxywfbn forum.dlang.org Ali
Jul 05 2017
On Wednesday, May 31, 2017 08:18:07 Vasileios Anagnostopoulos via Digitalmars-d-learn wrote:Hi, after reading various articles bout the "supposed" drawbacks of checked exceptions I started to have questions on nothrow. Why there exists and not a throws annotation enforced by the compiler? I understand that people are divided on checked exceptions and each side has some valid points. But explicitly marking a function as throwing "something" is another subject. Why have the dlang community reached to the decision to use nothrow and not a throws?Well, if you're not doing checked exceptions, the interesting question is really what _doesn't_ throw rather than what throws, because if the compiler knows that a function doesn't throw, it can optimize out the exception handling mechanisms that are normally required. Also, if nothrow wasn't there originally (and it probably wasn't), then adding an attribute to indicate that a function doesn't throw wouldn't have broken any existing code, whereas adding an attribute to indicate that an exception does throw would have broken all existing code that used exceptions. Also, given that exceptions are the normal error-handling mechanism for D, it makes more sense to allow them by default than to disallow them by default. Ultimately though, since one is a negation of the other, either an attribute indicating that a function does throw or one indicating that a function doesn't throw would work. Logically, they're the same. It's just a question of which makes more sense as a default and what effect adding the attribute would have had when it was originally introduced, both of which imply that nothrow is the better choice, even if it could have gone either way. Regardless, nothrow is what we have, and there really wouldn't be any benefit to switching it to throw (or throws or whatever) even if breaking code weren't a concern. - Jonathan M Davis
May 31 2017
On Wednesday, 31 May 2017 at 09:31:48 UTC, Jonathan M Davis wrote:[...]Thank you for the answers.
May 31 2017
On Wednesday, 31 May 2017 at 09:31:48 UTC, Jonathan M Davis wrote:On Wednesday, May 31, 2017 08:18:07 Vasileios Anagnostopoulos via Digitalmars-d-learn wrote:I don't think this is possible in current D? nothrow functions can still throw Error.[...]Well, if you're not doing checked exceptions, the interesting question is really what _doesn't_ throw rather than what throws, because if the compiler knows that a function doesn't throw, it can optimize out the exception handling mechanisms that are normally required.
Jul 05 2017
On Wednesday, 31 May 2017 at 08:18:07 UTC, Vasileios Anagnostopoulos wrote:Hi, after reading various articles bout the "supposed" drawbacks of checked exceptions I started to have questions on nothrow. Why there exists and not a throws annotation enforced by the compiler? I understand that people are divided on checked exceptions and each side has some valid points. But explicitly marking a function as throwing "something" is another subject. Why have the dlang community reached to the decision to use nothrow and not a throws?Adding throws to a function requires changing all the functions downstream. Adding nothrow doesn't.
Jul 05 2017