On 8/5/2013 11:30 AM, Bosak wrote: > On Monday, 5 August 2013 at 13:54:38 UTC, Adam D. Ruppe wrote: >> On Monday, 5 August 2013 at 13:42:01 UTC, Michal Minich wrote: >>> But what Bosak proposes is that when "with" statements ends, the >>> object should be destructed >> >> That would happen if the object is a struct, or wrapped in a struct, >> since it would go out of scope at the end of the with and call its >> destructor then. >> >> So then you could just go >> >> import std.typecons; >> with(auto a = Scoped!T()) { ... } >> >> and the Scoped destructor does the deleting. > > Exactly. My idea is to add third use case of with. Not there are 2 ways > to use with(of witch I know): > > 1) Declare something and use with to not repeat yourself: > auto foo = new Foo; > with(foo) { > name = "bar"; //foo.name = "bar"; > } > In this case it is only used for object construction and setup. And the > with statement doesn't destruct the object or anything like that. > 2) Used with types > struct Foo { > static int bar = 2; > } > with(Foo) { > bar++; //Foo.bar++; > } > Again with doesn't destruct or anything > > All of the above are currently available, but I want a third case to be > added: > > 3) Used when you declare something in the with statement with scope only > in the with statement > with(Foo foo = new Foo) { > name = "bar"; > } > After that foo's destructor gets called and since foo was in the scope > of with it goes out of scope and no references are made to foo. There > should be a constraint that you cannot take the address of foo in the > with statement(i.e assign a global to foo) > 3.1) Or used with rvalues?? > int[] values; > with(new Foo) { > name = "bar"; > values = getData(); //foo.getData() > } > //use values taken from foo > > I think that in case 3.1 it is very intuitive for using resources like > files. Instead of writing something like: > string text; > auto file = open("myfile.txt", "r"); > text = t.readlines(); > file.close(); > You can write this: > string text; > with(open("myfile.txt", "r")) { //no need to declare variable > text = readlines(); //just use the file to get the data > }//with automaticaly calls close() on the file, even if exception got > thrown > And if the exception got thrown in the declaration of the with block, > then the with block doesn't execute. For example in the above code if > the file didn't exist, an exception would be thrown from open and no > variable would be created. > > I hope that I have made my suggestion more clear.
IMO, using statements in C# are annoying. They make otherwise linear code much harder to read. The *idea* behind them makes total sense, but I dislike the implementation. Instead of writing this: public string[] GetLines(string name) { string result; using (var file = new File(name)) { result = file.ReadText(); } return result.split('\n'); } ...I would very much like to write this: public string[] GetLines(string name) { autodispose var file = new File(name1); string result = file.ReadText(); //file disposed after this line, since it's the last place it's used return result.split('\n'); } Another problem with C#'s using (){} is that it doesn't easily scale from single-method use to object-wide use. For example, would you want to add "using" statements to every single method in a controller just because all of them use the same database object?