if a condition occurs i have to stop the execution of the current method call and return to the state before the method call .how can i do it .. suppose a i am executing some sample method and a condition occurs and i am prompting a message box and then i want to return to state before this function call
- Does the executed method detect this condition or is it detected in some other thread?Ronald Wildenberg– Ronald Wildenberg2009-04-14 06:43:10 +00:00Commented Apr 14, 2009 at 6:43
- 1What do you mean "return to the state before the method call"? revert all assignments?Anton Tykhyy– Anton Tykhyy2009-04-14 06:45:00 +00:00Commented Apr 14, 2009 at 6:45
- This Question was asked in: stackoverflow.com/questions/744013/… as wellJesper Fyhr Knudsen– Jesper Fyhr Knudsen2009-04-14 07:10:31 +00:00Commented Apr 14, 2009 at 7:10
- It sounds like you're asking a few different questions here: 1. How to stop method execution; 2. How to revert the state of an object; Could you please clarify whether this is actually what you were asking, or whether you meant something different? Cheers.Smashery– Smashery2009-04-14 07:33:31 +00:00Commented Apr 14, 2009 at 7:33
7 Answers
If I'm understanding you correctly, you wish to undo changes you have made to certain variables if some condition is true? If that's the case, you will want to store a copy of all your variables (or your class as a whole). Then, if your condition comes up true, you'll have to revert all those variables to their initial state before returning from your function. It would be something like this:
// In order to clone your variable, you may need to inherit from // ICloneable and implement the Clone function. bool MyFunction(ICloneable c) { // 1. Create a copy of your variable ICloneable clone = c.Clone(); // 2. Do whatever you want in here ... // 3. Now check your condition if (condition) { // Copy all the attributes back across to c from your clone // (You'll have to write the ResetAttributes method yourself) c.ResetAttributes(clone); // Put a message box up MessageBox.Show("This failed!"); // Now let the caller know that the function failed return false; } else { // Let the caller know that the function succeeded return true; } } Comments
A generic rollback functionality on the heap is for me unheard of. But you can use the Command pattern to get undo functionality and use it for rolling back:
http://en.wikipedia.org/wiki/Command_pattern
Essentially you encapsulate an operation in an object that stores enough information of the change that it can undo it. You push that object onto a stack, and when your condition occurs, you go pop all command objects from the stack and undo them. Without more information about your case it's difficult to give more specific information or tell whether this is applicable for you.
Comments
This is what exceptions are for. You throw an exception to terminate the function and any caller, until an exception handler is reached.
Note that this should only be done if something exceptional has occurred; exceptions shouldn't be used as a "different kind of" return value, as they are more costly in terms of code size (whether thrown or not) and running time (if thrown) , than normals returns.
As far as returning to the state you had before, this is possible if your code and any library code through which the call proceeded was written in an exception safe manner.
Comments
Another solution, differing slightly from those above:
Check for the specified condition a bit now and then in your sample method.
public void MyMethod() { some code if (conditionOccurred == true){ reset to the previous state and exit;} more code } This is probably not according to the book, but it gives quite simple and readable code if you don't use it too often.
I probably don't have to mention that you need save the program's state if you want to be able to return to it, and you need to write some code that returns you to this state.
Comments
You can use the Memento pattern to implement object rollback. From here ...
The caretaker is going to do something to the originator, but wants to be able to undo the change. The caretaker first asks the originator for a memento object. Then it does whatever operation (or sequence of operations) it was going to do. To roll back to the state before the operations, it returns the memento object to the originator.
Once you receive the event that indicates that you should roll back, you can undo the change and return to the caller. Here is some info. and links on why you should not use Thread.Abort.