www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - 2 File IO Questions (Phobos)

reply Zane <zane.sims gmail.com> writes:
Hello all,

I have been looking at Phobos lately, and currently I am having some trouble
understanding what is going on with the following 2 trivial examples.  First of
all, I am using dmd v1.050.


bytes come from?
(1) ---------------------------------------------------------------->

import std.stream;
import std.stdio;

int main()
{
	char[] stuff = "This is some stuff!";

	File f = new File("stuff.txt", FileMode.Out | FileMode.In);
	f.write(stuff);
	f.seekSet(0);
	stuff = f.readLine();
	writef("[%s]", stuff);
	f.close;

	return 0;
}


This one I wanted to have a class open a file upon initialization of an
instance, and close a file when the destructor is called.  I get an "Error:
Access Violation" unless I comment out the file.close line.  Why?  (of course
this example also has the same problem as the first example, but I kept the
first one simpler to narrow down things)
(2) ---------------------------------------------------------------->

import std.stream;

public class StuffWriter
{
	File file;

	this(char[] filename)
	{
		file = new File(filename, FileMode.Out);
	}

	~this()
	{
		file.close; //this causes an access violation???
	}

	public void write(char[] stuff)
	{
		file.write(stuff);
	}
}

int main()
{
	StuffWriter sw = new StuffWriter("stuff.txt");
	sw.write("This is some stuff!");

	return 0;
}


Thanks!
Zane
Nov 07 2009
parent reply Zane <zane.sims gmail.com> writes:
Zane Wrote:

 Hello all,
 
 I have been looking at Phobos lately, and currently I am having some trouble
understanding what is going on with the following 2 trivial examples.  First of
all, I am using dmd v1.050.
 

bytes come from?
 (1) ---------------------------------------------------------------->
 
 import std.stream;
 import std.stdio;
 
 int main()
 {
 	char[] stuff = "This is some stuff!";
 
 	File f = new File("stuff.txt", FileMode.Out | FileMode.In);
 	f.write(stuff);
 	f.seekSet(0);
 	stuff = f.readLine();
 	writef("[%s]", stuff);
 	f.close;
 
 	return 0;
 }
 
 
 This one I wanted to have a class open a file upon initialization of an
instance, and close a file when the destructor is called.  I get an "Error:
Access Violation" unless I comment out the file.close line.  Why?  (of course
this example also has the same problem as the first example, but I kept the
first one simpler to narrow down things)
 (2) ---------------------------------------------------------------->
 
 import std.stream;
 
 public class StuffWriter
 {
 	File file;
 
 	this(char[] filename)
 	{
 		file = new File(filename, FileMode.Out);
 	}
 
 	~this()
 	{
 		file.close; //this causes an access violation???
 	}
 
 	public void write(char[] stuff)
 	{
 		file.write(stuff);
 	}
 }
 
 int main()
 {
 	StuffWriter sw = new StuffWriter("stuff.txt");
 	sw.write("This is some stuff!");
 
 	return 0;
 }
 
 
 Thanks!
 Zane
Doh! I still need help with number 2, but for number 1, all I needed was to use 'writeString' instead of 'write'. Like I said, still getting used to Phobos. Thanks, Zane
Nov 07 2009
parent reply Frank Benoit <keinfarbton googlemail.com> writes:
Zane schrieb:
 Doh! I still need help with number 2, but for number 1, all I needed
 was to use 'writeString' instead of 'write'.  Like I said, still
 getting used to Phobos.  Like I said, I still need help on the

 
 Thanks, Zane
desctructors are called in not defined order. The GC puts your class instance 'sw' and the File instance 'sw.file' onto the list for destruction. So the 'sw.file' might be destructed before 'sw' is. Deferencing sw.file from withing sw.~this then fails. A general rule: in a dtor, never dereference member variables. You have to rely on the File dtor, to close himself if still open.
Nov 07 2009
parent Zane <zane.sims gmail.com> writes:
Frank Benoit Wrote:

 Zane schrieb:
 Doh! I still need help with number 2, but for number 1, all I needed
 was to use 'writeString' instead of 'write'.  Like I said, still
 getting used to Phobos.  Like I said, I still need help on the

 
 Thanks, Zane
desctructors are called in not defined order. The GC puts your class instance 'sw' and the File instance 'sw.file' onto the list for destruction. So the 'sw.file' might be destructed before 'sw' is. Deferencing sw.file from withing sw.~this then fails. A general rule: in a dtor, never dereference member variables. You have to rely on the File dtor, to close himself if still open.
I understand, thanks very much!
Nov 07 2009