Why is this file not actually writing to disk?
Question
Hi guys as a homework i have to write a program that read from a file that contain the folowing:
toto, M, 50
fifi, F, 60
soso, F, 70
lolo, M, 60
fifi, F, 60
and then find the following: Which mark is most repeated and how many times is it repeated
avgerage all students
avgerage all male
avgerage all female
how many are below avgerage mark
how many more than avgerage mark
and reverse
how many students' names start with T and end with T in a file
(all results should be placed in an out file)
I've done it all with no errors but its not writing on the file can any one tell me why and please i dont want to use any new methods as (LINQ and other advance stuff)
using System;
using System.Collections.Generic;
using System.Text;
using System.IO;
namespace Exam_Ex
{
class Program
{
public static int[] ReadFile(string FileName, out string[] Name, out char[] Gender)
{
Name = new string[1];
int[] Mark = new int[1];
Gender = new char[1];
if (File.Exists(FileName))
{
FileStream Input = new FileStream(FileName, FileMode.Open, FileAccess.Read);
StreamReader SR = new StreamReader(Input);
string[] Current;
int Counter = 0;
string Str = SR.ReadLine();
while (Str != null)
{
Current = Str.Split(',');
Name[Counter] = Current[0];
Mark[Counter] = int.Parse(Current[2]);
Gender[Counter] = char.Parse(Current[1].ToUpper());
Counter++;
Array.Resize(ref Name, Counter + 1);
Array.Resize(ref Mark, Counter + 1);
Array.Resize(ref Gender, Counter + 1);
Str = SR.ReadLine();
}
}
return Mark;
}
public static int MostFreq(int[] M, out int Frequency)
{
int Counter = 0;
int Frequent = 0;
Frequency = 0;
for (int i = 0; i < M.Length; i++)
{
Counter = 0;
for (int j = 0; j < M.Length; j++)
if (M[i] == M[j])
Counter++;
if (Counter > Frequency)
{
Frequency = Counter;
Frequent = M[i];
}
}
return Frequent;
}
public static int Avg(int[] M)
{
int total = 0;
for (int i = 0; i < M.Length; i++)
total += M[i];
return total / M.Length;
}
public static int AvgCond(char[] G, int[] M, char S)
{
int total = 0;
int counter = 0;
for (int i = 0; i < G.Length; i++)
if (G[i] == S)
{
total += M[i];
counter++;
}
return total / counter;
}
public static int BelowAvg(int[] M, out int AboveAvg)
{
int Bcounter = 0;
AboveAvg = 0;
for (int i = 0; i < M.Length; i++)
{
if (M[i] < Avg(M))
Bcounter++;
else
AboveAvg++;
}
return Bcounter;
}
public static int CheckNames(string[] Name, char C)
{
C = char.Parse(C.ToString().ToLower());
int counter = 0;
string Str;
for (int i = 0; i < Name.Length - 1; i++)
{
Str = Name[i].ToLower();
if (Str[0] == C || Str[Str.Length - 1] == C)
counter++;
}
return counter;
}
public static void WriteFile(string FileName, string[] Output)
{
FileStream FS = new FileStream(FileName, FileMode.OpenOrCreate, FileAccess.Write);
StreamWriter SW = new StreamWriter(FS);
for (int i = 0; i < Output.Length; i++)
SW.WriteLine(Output[i]);
}
static void Main(string[] args)
{
int[] Mark;
char[] Gender;
string[] Name;
string[] Output = new string[8];
int Frequent, Frequency, AvgAll, MaleAvg, FemaleAvg, BelowAverage, AboveAverage, NamesCheck;
Mark = ReadFile("c:\\IUST1.txt", out Name, out Gender);
Frequent = MostFreq(Mark, out Frequency);
AvgAll = Avg(Mark);
MaleAvg = AvgCond(Gender, Mark, 'M');
FemaleAvg = AvgCond(Gender, Mark, 'F');
BelowAverage = BelowAvg(Mark, out AboveAverage);
NamesCheck = CheckNames(Name, 'T');
Output[0] = "Frequent Mark = " + Frequent.ToString();
Output[1] = "Frequency = " + Frequency.ToString();
Output[2] = "Average Of All = " + AvgAll.ToString();
Output[3] = "Average Of Males = " + MaleAvg.ToString();
Output[4] = "Average Of Females = " + FemaleAvg.ToString();
Output[5] = "Below Average = " + BelowAverage.ToString();
Output[6] = "Above Average = " + AboveAverage.ToString();
Output[7] = "Names With \"T\" = " + NamesCheck.ToString();
WriteFile("d:\\output.txt", Output);
}
}
}
Thanx in advance
Solution
I haven't test it. But you should call SW.close()
after finished writing stuffs.
OTHER TIPS
The other answers talk about calling Close explicitly - I would suggest that instead of doing that, you wrap the use of the StreamWriter (and StreamReader and streams) in a using
statement, e.g.
using (StreamWriter SW = new StreamWriter(FS))
{
for (int i = 0; i < Output.Length; i++)
{
SW.WriteLine(Output[i]);
}
}
This will call Dispose
automatically, which will close the appropriate resource. Manually calling Close
just at the end of the method is vulnerable to exceptions - you'd normally want to put it in a finally
block, but that's what the using
statement does automatically.
In the WriteFile method, after SW.WriteLine(Output[i]);, execute SW.Close();
I believe the buffer isn't emptied until you call Close();