count grade while looping by using answer in streamwriter? - c#

Can someone look at my code? How do I count the grade while looping, or can I take the line from StreamWriter and put substring?
I keep making it more and more messy... and I need to display it like
Student that score A got how many?
Student that got B got how many?>
student that got C how many>
student that got d ... f...
using (StreamReader reader = new StreamReader("Student.txt"))
{
StreamWriter output = new StreamWriter("Result.txt");
String line;
line = reader.ReadLine();
while (line != null)
{
String name = line.Substring(0, 9);
String Asg1 = line.Substring(10, 3);
String Asg2 = line.Substring(16, 3);
String Test = line.Substring(22, 3);
String Quiz = line.Substring(28, 3);
String Exam = line.Substring(34, 3);
int intAsg1 = int.Parse(Asg1);
int intAsg2 = int.Parse(Asg2);
int intTest = int.Parse(Test);
int intQuiz = int.Parse(Quiz);
int intExam = int.Parse(Exam);
int percentAsg1 = (intAsg1 * 25) / 100;
int percentAsg2 = (intAsg2 * 25) / 100;
int percentTest = (intTest * 10) / 100;
int percentQuiz = (intQuiz * 10) / 100;
int percentExam = (intExam * 30) / 100;
// this part i dont get it~
**String Grade;
if (overallScore >= 70)
{
Grade = "A";
}
else if (overallScore >= 60)
{
Grade = "B";
}
else if (overallScore >= 50)
{
Grade = "C";
}
else if (overallScore >= 40)
{
Grade = "D";
}
else
{
Grade = "F";
}
}
}

It's not looping.
while !reader.EndOfStream
{
/*now check each Readline.
parse each line and create a new grade object for
each iteration and add to collection*/
}
A custom class to store the data for each student:
public class grade
{
public int asg1{ get; set; }
public int asg2{ get; set; }
public int test{ get; set; }
public int quiz{ get; set; }
public int exam{ get; set; }
//whatever else you need
}
A collection of Grades:
var grades = New List<grade>

I think you are looking for a class to hold the results in addition to correcting the readline loop.
public class Student
{
public string Name { get; set; }
public List<Grade> Grades { get; set; }
}
Then create a list before you start the loop
var students = new List<Student>();
Then add to the list in each iteration

Related

For loop takes the the max count

private List<SurveyDetail> GetSurveyDetails()
{
List<SurveyDetail> surveyDetails = new List<SurveyDetail>();
SurveyDetail detail = new SurveyDetail();
int cid = 0;
for (int i = 1; i < 3; i++)
{
detail.choiceId = "1";
detail.choiceDesc = "tesT";
detail.questionId = i.ToString();
surveyDetails.Add(detail);
}
return surveyDetails;
}
public class SurveyDetail
{
public string questionId { get; set; }
public string choiceId { get; set; }
public string choiceDesc { get; set; }
}
when I run the code it question Id always gives me the last number of i that was run for example, in this case, it gives me 2. It gives me 2 on both counts.
Where I want the questionid to be 1 in the first count and 2 in the second.
You should move SurveyDetail initialization into the for body
private List<SurveyDetail> GetSurveyDetails()
{
List<SurveyDetail> surveyDetails = new List<SurveyDetail>();
int cid = 0;
for (int i = 1; i < 3; i++)
{
SurveyDetail detail = new SurveyDetail();//<==NOTE THIS
detail.choiceId = "1";
detail.choiceDesc = "tesT";
detail.questionId = i.ToString();
surveyDetails.Add(detail);
}
return surveyDetails;
}
Incase you want to use : LINQ
var result = Enumerable.Range(1, 3).Select(detail => new SurveyDetail
{
choiceId = "1",
questionId = detail.ToString(),
choiceDesc = "testT",
});

Initializing Array in Class c#

There is a method to read data from file
public static void ReadData(out StudentMarks[] Students, out int amount)
{
amount = 0;
Students = new StudentMarks[Max];
using (StreamReader reader = new StreamReader("C:\\Users\\Andrius\\Desktop\\Mokslams\\C#\\Pratybos\\P3\\P3.2\\StudentsMarks.csv"))
{
reader.ReadLine(); reader.ReadLine();
string line = null;
int[] marks;
marks = new int[Max];
while (null != (line = reader.ReadLine()))
{
string[] values = line.Split(',');
string surname = values[0];
string name = values[1];
string group = values[2];
int amountOfMarks = int.Parse(values[3]);
int i = 0; int yMax = 3 + amountOfMarks;int yMin = 4;
while (amountOfMarks >= i)
{
if (yMin <= yMax)
{
marks[i] = int.Parse(values[yMin]);
yMin++;
}
i++;
}
StudentMarks MarksObj = new StudentMarks(surname, name, group, amountOfMarks, marks);
Students[amount++] = MarksObj;
}
}
}
There is a class:
class StudentMarks
{
public const int Max = 50;
public string Surname { get; set; }
public string Name { get; set; }
public string Group { get; set; }
public int AmountOfMarks { get; set; }
public int[] Marks { get; set; }
public StudentMarks(string surname, string name, string group, int amountOfMarks, int[] marks)
{
Surname = surname;
Name = name;
Group = group;
AmountOfMarks = amountOfMarks;
Marks = marks;
}
}
The thing is, I cannot read "Marks", because I dont know how to initialize array in Class. My method should be working fine, I just can't put marks[i] into Students[i].Marks[y]
I don't understand why you want this.
but do you want like it?
class StudentMarks
{
public const int Max = 50;
public string Surname { get; set; }
public string Name { get; set; }
public string Group { get; set; }
public int[] Marks { get; private set; }
public StudentMarks(string surname, string name, string group, int amountOfMarks)
{
Surname = surname;
Name = name;
Group = group;
Marks = new int[amountOfMarks];
}
}
public static void ReadData(out StudentMarks[] Students, out int amount)
{
amount = 0;
Students = new StudentMarks[Max];
using (StreamReader reader = new StreamReader("C:\\Users\\Andrius\\Desktop\\Mokslams\\C#\\Pratybos\\P3\\P3.2\\StudentsMarks.csv"))
{
reader.ReadLine(); reader.ReadLine();
string line = null;
while (null != (line = reader.ReadLine()))
{
string[] values = line.Split(',');
string surname = values[0];
string name = values[1];
string group = values[2];
int i = 0; int yMax = 3 + amountOfMarks;int yMin = 4;
Students[amount] = new StudentMarks(surname, name, group, amountOfMark);
while (amountOfMarks >= i)
{
if (yMin <= yMax)
{
Students[amount].Marks[i] = int.Parse(values[yMin]);
yMin++;
}
i++;
}
amount++;
}
}
}

C# cannot convert Int to Double

I get the error converting Int to Double, my next line Average[y] = Average[y] + Students[i].Marks; is not working either. So how can convert int[] to double[]?
public static double[] Averages(StudentMarks[] Students, int amount, string[] DifferentGroups, int GroupAmount, out double[] Average)
{
Average = new double[Max];
int y = 0;
int CountGroups = 0;
//int sum = 0;
for (int i = 0; i < amount; i++)
{
if (Students[i].Group == DifferentGroups[y])
{
Convert.ToDouble(Students[i].Marks);
//Average[y] = Average[y] + Students[i].Marks;
}
}
return Average;
}
The main:
static void Main(string[] args)
{
int amount;
StudentMarks[] Students;
string[] DifferentGroups;
int GroupAmount;
double[] Average;
ReadData(out Students, out amount);
DifferentGroups = FindDifferentGroups(Students, amount, out DifferentGroups, out GroupAmount);
Average = Averages(Students, amount, DifferentGroups, GroupAmount, out Average);
Class:
public const int Max = 50;
public string Surname { get; set; }
public string Name { get; set; }
public string Group { get; set; }
public int AmountOfMarks { get; set; }
public int[] Marks { get; set; }
So Student[i].Marks is Array.
Convert.ToDouble returns a double - it does not make an integer property or variable a double.
I think you want:
if (Students[i].Group == DifferentGroups[y])
{
double mark = Convert.ToDouble(Students[i].Marks);
Average[y] = Average[y] + mark;
}
or just:
if (Students[i].Group == DifferentGroups[y])
{
Average[y] = Average[y] + Convert.ToDouble(Students[i].Marks);
}
All Convert.ToXXX functions return the new value. Therefore, you should be expecting that and assigning the return value to a local variable.
Something like:
double YourMark = Convert.ToDouble(Students[i].Marks);
So how can convert int[] to double[]?
By programming. You write code to do it.
var d = new double[Students[i].Marks.Length];
for (int j = 0; j < Students[i].Marks.Length; ++j)
{
d[j] = Convert.ToDouble(Students[i].Marks[j]);
}
Or use LINQ:
var d = Students[i].Marks.Select(n => Convert.ToDouble(n)).ToArray();
Next time a method call won't compile or doesn't work the way you hoped it might, a good first step would be to check the documentation.

Loop object creation

I need to have my second nested for loop send the array values to class friends.
I do not know how I would go about this?
Unless I missed something in the class?
namespace List
{
class Program
{
public const int ARRAYSIZE = 5;
static void Main()
{
string[] relSend = { "Enter name", "enter phone number", "enter 2 didigt month dob", "enter 2 digit day dob", "enter 2 digit dob year" };
string[] In = new string[5];
string[] answer = new string[10];
for (int x = 0; x <= 8; x++)
{
for (int i = 0; i < relSend.Length; i++)
{
WriteLine("{0}", relSend[i]);
In[i] = Console.ReadLine();
}
for (int i = 0; i < In.Length; i++)
{
}
}
}
}
}
public class Friends
{
public string Name { get; set; }
public int Phone { get; set; }
public int Month { get; set; }
public int Day { get; set; }
}
I guess you mean you want to create an object out of the information collected, that is no problem:
List<Friend> friends = new List<Friend>();
for (int x = 0; x <= 8; x++)
{
for (int i = 0; i < relSend.Length; i++)
{
WriteLine("{0}", relSend[i]);
In[i] = Console.ReadLine();
}
friends.Add( new Friend() { Name = In[0]
, Phone = int.Parse(In[1])
, Month = int.Parse(In[2])
, Day = int.Parse(In[3])
, Year = int.Parse(In[4])
}
);
}
Make sure to validate the input before creating the object! Also, I would suggest to use string for a phone number since you would lose the 0 that is the usual prefix. Month, Day and Year might be combined in a single DateTime.
Tell me if you need any explanations:
namespace List
{
class Program
{
//Create a dictionary to find out each question is realated to which property.
private static Dictionary<string, string> questions = new Dictionary<string, string>();
static void Main()
{
questions.Add("Enter name", "Name");
questions.Add("enter phone number", "Phone");
questions.Add("enter 2 didigt month dob", "Month");
questions.Add("enter 2 digit day dob", "Day");
questions.Add("enter 2 digit dob year", "Year");
//Create list of friends
List<Friends> friendsList = new List<Friends>();
for (int x = 0; x <= 8; x++)
{
Friends f = new Friends();
foreach (string q in questions.Keys)
{
Console.WriteLine("{0}", q);
//Find property using Sytem.Reflection
System.Reflection.PropertyInfo property = f.GetType().GetProperty(questions[q]);
//Set value of found property
property.SetValue(f, Convert.ChangeType(Console.ReadLine(), property.PropertyType), null);
}
//Add a friend to list
friendsList.Add(f);
}
}
}
}
public class Friends
{
public string Name { get; set; }
public int Phone { get; set; }
public int Year { get; set; }
public int Month { get; set; }
public int Day { get; set; }
}

Fill a list with objects depending on eachothers attributes

I have a List where I want to use the latest object created in the List to calculate the next objects attributes. I'm not sure how to write the loop doing that. Can you help me with that?
public ActionResult ShowDetail(DateTime startdate, double PresentValue, double InterestRate, double FutureValue, int PaymentPeriods)
{
List<Calculation> cList = new List<Calculation>();
Calculation calc = new Calculation();
calc.Date = startdate.ToShortDateString();
calc.InvoiceAmount = 2000;
calc.InterestRate = InterestRate;
calc.InterestAmount = (PresentValue * InterestRate / 360 * 30);
calc.Amortization = (2000 - (PresentValue * InterestRate / 360 * 30));
calc.PresentValue = PresentValue;
cList.Add(calc);
for (int i = 0; i < PaymentPeriods; i++)
{
cList.Add(new Calculation()
{
var calcBefore = cList.GetLastObject //Some how I want to take the object before the one i want to create
cList.Add(new Calculation()
{
Date = calcBefore.Date.Add(1).Month() //something like this
InvoiceAmount = calcBefore.InvoiceAmount
InterestRate = calcBefore.InterestRate
InterestAmount = (calcBefore.PresentValue * InterestRate / 360 * 30) //I want to take the presentvalue from the object before in the List and use that to calculate the the next InterestAmount
//And so on
}
});
}
return PartialView("ShowDetail", cList);
}
Calculation:
public partial class Calculation
{
public string Date { get; set; }
public double InvoiceAmount { get; set; }
public double InterestRate { get; set; }
public double InterestAmount { get; set; }
public double Amortization { get; set; }
public double PresentValue { get; set; }
}
You can use the index of the list to access the last inserted:
var calcBefore = cList[cList.Count - 1];
another way which does the same: Enumerable.Last:
var calcBefore = cList.Last();
Since you have added one before the loop the list is not empty and this is safe.
Here is the complete loop:
for (int i = 0; i < PaymentPeriods; i++)
{
calc = new Calculation();
Calculation calcBefore = cList[cList.Count - 1];
calc.Date = DateTime.Parse(calcBefore.Date).AddMonths(1).ToString();
calc.InvoiceAmount = calcBefore.InvoiceAmount;
calc.InterestRate = calcBefore.InterestRate;
calc.InterestAmount = (calcBefore.PresentValue * InterestRate / 360 * 30);//I want to take the presentvalue from the object before in the List and use that to calculate the the next InterestAmount
cList.Add(calc);
}
According to the Date, i assume you want to add one month, use DateTime.AddMonths:
Date = DateTime.Parse(calcBefore.Date).AddMonths(1).ToString();
However, i wouldn't use a String for a DateTime at all.
do not think you would use a loop,
All you would have to do is have a constructor take an Calculation object as a parameter.
Then you would do something like
public partial class Calculation
{
public string Date { get; set; }
public double InvoiceAmount { get; set; }
public double InterestRate { get; set; }
public double InterestAmount { get; set; }
public double Amortization { get; set; }
public double PresentValue { get; set; }
public Calculation (Calculation as calculation(
{
.. set you prop
}
}
then when you call a new object, you pass in the last object in the current list
var newObj = new Calculation(cList[cList.Length -1]);

Categories