2014-11-03 2 views
0

학생 시험 점수 신청서를 작성해야합니다.
학생 이름을 저장하는 구조, 5 개의 테스트 점수를 보유 할 배열 및 평균 점수가 있습니다. 저는 6 명의 학생들을위한 구조의 배열을 만들었습니다. 사용자 입력은 텍스트 상자를 통해 설정됩니다. 각 학생의 평균을 계산해야합니다. 할당 요구 사항 : 응용 프로그램에는 Name (문자열), Test Scores (5 개의 double 형식의 배열) 및 Average (double 형식)을 저장하는 구조가 있어야합니다. 6 명의 학생과 일치하는 6 개의 구조 변수가 있어야합니다. 사용자가 각 학생의 데이터를 입력하고 각 학생의 평균 시험 점수를 계산할 수 있어야합니다. 사용자는 등의 파일에/인쇄 데이터를 저장 읽을 수 있어야합니다학생 시험 점수 평균 계산 잘못 함

나는이에 대한 몇 가지 게시물을 읽었지만 수 없었던 100

은 0 아래 이상 점수를 받아 들일해야

기존 게시물로 해결하고 지난 2 일 동안 해결하려고 노력했습니다. 지금 나는 정확한 평균을 얻지 못하고있다.
정보를 인쇄하고 검색 할 수 있어야하지만이 문제를 해결할 것입니다. 저는 학생을위한 최대 카운트에서 5와 6을 시험했으며 테스트의 최대 카운트는 4와 5를 시도했습니다. 내가 가진 숫자는 정확하다고 생각하지만 게시물 중 많은 수가 다른 숫자를 사용합니다. 그러나이 숫자를 사용할 때 디버그 모드로 실행했을 때 학생 수는 7이되어 100 % 확실하지는 않지만 이것이 정확하다고 생각합니까? . 그것은 합계가 올바르게 추가되지 않는 것으로 보입니다. 나는 여러 가지 방법을 시도해 보았고 심지어 다음 숫자로 넘어 가기 전에 0으로 다시 초기화하려고 시도했지만 지금까지 시도한 것은 아무것도 없습니다. 따라서 각 성적 그룹에 대해 다른 Try Catch 문을 사용해야하는 이유입니다. 내가 따로 보관해야 할 수도 있기 때문에 지금 당장 떠났다.

여기 내 코드입니다. 어떤 도움을 주셔서 감사합니다.
fyi - Imports System.IO에서 코드가 시작되지 않습니다. 따라서 'Enter code here'아래의 초기 코드가 vb로 표시되지 않습니다. 향후 게시물을 수정하는 방법을 알려주세요.

감사합니다.

Imports System.IO 

Public Class Form1 

    'Class level variables 
    Const intMAX_STUDENTS As Integer = 5 'Number of Students 
    Const intMAX_TESTS As Integer = 4 'Number of Tests 
    Private strFilename As String = "StudentReport.txt" 'Document File name 

    Private student(intMAX_STUDENTS) As StudentRecord 'Array for student names 

    Structure StudentRecord 

     Dim strStudent As String 
     Dim dblTestScores() As Double 
     Dim dblAverage As Double 
    End Structure 

    Sub CalcAverage() 

     ImportNames() 

     'Variable to hold the total of the grades. 
     Dim dblGradesTotal0 As Double = 0 
     Dim dblGradesTotal1 As Double = 0 
     Dim dblGradesTotal2 As Double = 0 
     Dim dblGradesTotal3 As Double = 0 
     Dim dblGradesTotal4 As Double = 0 
     Dim dblGradesTotal5 As Double = 0 

     'Add scores to the array 
     For intIndex = 0 To intMAX_STUDENTS 
      ReDim student(intIndex).dblTestScores(4) 'Scores per student 
     Next 

     Try 
      'Get grades for first student 
      student(0).dblTestScores(0) = ValidInput(CDbl(txtGrade00.Text)) 
      student(0).dblTestScores(1) = ValidInput(CDbl(txtGrade01.Text)) 
      student(0).dblTestScores(2) = ValidInput(CDbl(txtGrade02.Text)) 
      student(0).dblTestScores(3) = ValidInput(CDbl(txtGrade03.Text)) 
      student(0).dblTestScores(4) = ValidInput(CDbl(txtGrade04.Text)) 

      For Each i As StudentRecord In student 
       For Each a As Double In i.dblTestScores 
        dblGradesTotal0 += a 
       Next 
      Next 

      lblAvg0.Text = CStr(dblGradesTotal0/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 

     Try 
      'Get grades for second student 
      student(1).dblTestScores(0) = ValidInput(CDbl(txtGrade10.Text)) 
      student(1).dblTestScores(1) = ValidInput(CDbl(txtGrade11.Text)) 
      student(1).dblTestScores(2) = ValidInput(CDbl(txtGrade12.Text)) 
      student(1).dblTestScores(3) = ValidInput(CDbl(txtGrade13.Text)) 
      student(1).dblTestScores(4) = ValidInput(CDbl(txtGrade14.Text)) 

      For Each i As StudentRecord In student 
       For Each b As Double In i.dblTestScores 
        dblGradesTotal1 += b 
       Next 
      Next 

      lblAvg1.Text = CStr(dblGradesTotal1/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 

     Try 
      'Get grades for third student 
      student(2).dblTestScores(0) = ValidInput(CDbl(txtGrade20.Text)) 
      student(2).dblTestScores(1) = ValidInput(CDbl(txtGrade21.Text)) 
      student(2).dblTestScores(2) = ValidInput(CDbl(txtGrade22.Text)) 
      student(2).dblTestScores(3) = ValidInput(CDbl(txtGrade23.Text)) 
      student(2).dblTestScores(4) = ValidInput(CDbl(txtGrade24.Text)) 

      For Each i As StudentRecord In student 
       For Each c As Double In i.dblTestScores 
        dblGradesTotal2 += c 
       Next 
      Next 

      lblAvg2.Text = CStr(dblGradesTotal2/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 

     Try 
      'Get grades for fourth student 
      student(3).dblTestScores(0) = ValidInput(CDbl(txtGrade30.Text)) 
      student(3).dblTestScores(1) = ValidInput(CDbl(txtGrade31.Text)) 
      student(3).dblTestScores(2) = ValidInput(CDbl(txtGrade32.Text)) 
      student(3).dblTestScores(3) = ValidInput(CDbl(txtGrade33.Text)) 
      student(3).dblTestScores(4) = ValidInput(CDbl(txtGrade34.Text)) 

      For Each i As StudentRecord In student 
       For Each d As Double In i.dblTestScores 
        dblGradesTotal3 += d 
       Next 
      Next 

      lblAvg3.Text = CStr(dblGradesTotal3/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 

     Try 
      'Get grades for fifth student 
      student(4).dblTestScores(0) = ValidInput(CDbl(txtGrade40.Text)) 
      student(4).dblTestScores(1) = ValidInput(CDbl(txtGrade41.Text)) 
      student(4).dblTestScores(2) = ValidInput(CDbl(txtGrade42.Text)) 
      student(4).dblTestScores(3) = ValidInput(CDbl(txtGrade43.Text)) 
      student(4).dblTestScores(4) = ValidInput(CDbl(txtGrade44.Text)) 

      For Each i As StudentRecord In student 
       For Each e As Double In i.dblTestScores 
        dblGradesTotal4 += e 
       Next 
      Next 

      lblAvg4.Text = CStr(dblGradesTotal4/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 

     Try 
      'Get grades for sixth student 
      student(5).dblTestScores(0) = ValidInput(CDbl(txtGrade50.Text)) 
      student(5).dblTestScores(1) = ValidInput(CDbl(txtGrade51.Text)) 
      student(5).dblTestScores(2) = ValidInput(CDbl(txtGrade52.Text)) 
      student(5).dblTestScores(3) = ValidInput(CDbl(txtGrade53.Text)) 
      student(5).dblTestScores(4) = ValidInput(CDbl(txtGrade54.Text)) 

      For Each i As StudentRecord In student 
       For Each f As Double In i.dblTestScores 
        dblGradesTotal5 += f 
       Next 
      Next 

      lblAvg5.Text = CStr(dblGradesTotal5/intMAX_TESTS) 
     Catch ex As Exception 
      MessageBox.Show("Be sure to enter a valid numeric score") 
     End Try 
    End Sub 

    Private Sub mnuFileOpen_Click(sender As Object, e As EventArgs) Handles mnuFileOpen.Click 

    End Sub 

    Private Sub mnuFileSave_Click(sender As Object, e As EventArgs) Handles mnuFileSave.Click 

    End Sub 

    Private Sub mnuFilePrint_Click(sender As Object, e As EventArgs) Handles mnuFilePrint.Click 

    End Sub 

    Private Sub mnuFileExit_Click(sender As Object, e As EventArgs) Handles mnuFileExit.Click 

     Me.Close() 
    End Sub 

    Private Sub mnuReportClear_Click(sender As Object, e As EventArgs) Handles mnuReportClear.Click 

    End Sub 

    Private Sub mnuHelpAbout_Click(sender As Object, e As EventArgs) Handles mnuHelpAbout.Click 

     MessageBox.Show("This contains information regarding the Student Test Scores Application") 
    End Sub 

    Private Sub btnCalc_Click(sender As Object, e As EventArgs) Handles btnCalc.Click 

     CalcAverage() 
    End Sub 

    Public Function ValidInput(ByVal score As Double) As Double 

     If score >= 0 And score <= 100 Then 
      Return (score) 
     Else 
      Return MessageBox.Show("Please enter a valid test score between 0 and 100") 
     End If 
    End Function 

    Sub ImportNames() 

     student(0).strStudent = txtStudent0.Text 
     student(1).strStudent = txtStudent1.Text 
     student(2).strStudent = txtStudent2.Text 
     student(3).strStudent = txtStudent3.Text 
     student(4).strStudent = txtStudent4.Text 
     student(5).strStudent = txtStudent5.Text 
    End Sub 
End Class 
+1

커뮤니티에서 응답을 얻으려면 작동하는 것과 수행하지 않는 것에 대해보다 구체적으로 설명하고 오류 메시지를 포함하고 관련 부분 만 코드를 정리하십시오. http://stackoverflow.com/help/how-to-ask –

답변

1

에 오신 것을 환영합니다. 앞으로는 모든 코드가 아닌 관련 코드 만 게시하십시오. 이 경우 관련 코드는 점수와 평균을 얻은 것이므로 Try-Catch 블록 중 하나 일 것이고 모든 코드와 나머지 코드를 합한 것이 아닙니다.

당신이보고있는 것을 정확히 알지 못해도 평균이 올바르게 나오지 않는 이유는 계산 방법 때문이라고 생각합니다. 예를 들어

For Each i As StudentRecord In student 
    For Each f As Double In i.dblTestScores 
     dblGradesTotal5 += f 
    Next 
Next 

외부 루프는 모든 student 배열 구조를 통해 이동된다.

내부 루프는 그 학생의 모든 점수를 합산합니다.

그리고 다음 학생에게 가서 .... 그 학생 점수의 합계를 이전 학생의 점수 합계에 더하십시오.

해당 학생의 점수에 대해 하나의 루프 만 있으면됩니다.그런 다음이 줄

For Each f As Double In student(5).dblTestScores 
    dblGradesTotal5 += f 
Next 

: 당신은 이미 배열 구조의 인덱스, 그래서 이것을 알고

lblAvg5.Text = CStr(dblGradesTotal5/intMAX_TESTS) 

당신에게 그 학생의 평균을 줄 것이다.

몇 가지 사소한 사항을 고려해야합니다.

  1. 귀하의 블록은 매번 똑같은 작업을 수행합니다. 방법 (Sub)에 해당 코드를 리팩토링하고 ValidInput 함수에서 손가락과 키보드 :

  2. 을 저장, 당신은 Double로 반환 유형을 지정하지만 Else 블록에 당신은 MessageBox.Show을 반환합니다. 컴파일 할 수 있을지조차 모르겠지만 VB.NET은 C#만큼 까다롭지는 않습니다. 어떤 경우 든 오류를 의미하는 Else (-1은 좋음)에서 double을 반환하고 ValidInput이라는 메서드에서 메시지 상자를 팝합니다.

입력 검증 예

유효성 검사 사용자 입력은 당신이 그렇게하고있는 것이 중요하고, 그것의 좋은. "사용자의 의견을 절대 신뢰하지 마세요"라는 프로그래밍에 옛말이 있습니다.

현재 접근법의 문제점은 유효성 검사 결과에 따라 두 항목 중 하나를 반환하려는 것이고 out 매개 변수를 사용하지 않는 한 메서드에서 한 유형 만 반환 할 수 있다는 것입니다.

일반적으로 형식 변환을 시도 할 때 변환 (구문 분석)이 성공했는지 여부에 대한 부울 값을 반환하고 출력 매개 변수 (두 번째 매개 변수)의 구문 분석 결과를 반환하기 때문에 형식을 변환 할 때 TryParse을 사용하는 것이 좋습니다. . 이렇게하면 변환에 실패하면 추악한 런타임 오류가 발생하지 않습니다. 또한 CDbl 함수는 Visual Basic (pre .NET)의 보류 오버이며 일반적으로 기본 제공 .NET 변환 연산자를 사용하는 것이 좋습니다. 다음과 같이 될 것이라고 할

한 가지 방법 :

Dim score As Double 

If Double.TryParse(txtGrade50.Text, score) AndAlso (score >= 0 And score <= 100) Then 
    student(5).dbltTestScores(0) = score 
Else 
    MessageBox.Show("Please enter a valid test score between 0 and 100") 
End If 

참고 위의 If 문에 AndAlso의 사용 -이 단락 논리를 제공합니다. TryParse이 실패하면 다른 것을 평가하지 않습니다.

위의 단점은 이제 반복 할 코드가 많다는 것입니다. 또 다른 단점은 배열에 할당하기 전에 입력을 바로 평가한다는 것이고 사용자에게 잘못된 입력이 무엇인지 알려주지 않는다는 것입니다.

구조체의 배열에 값을 할당하기 전에 모든 입력의 유효성을 검사하는 것이 좋습니다. 그러면 사용자에게 어떤 값이 잘못되었는지 알려주고 오류를 수정하고 다시 시도 할 수 있습니다.

여기서 중요한 것은 데이터가 (올바른 제한 내)인지 확인한 후 처리해야한다는 것입니다. 다른 것들은 매우 추악하고 지저분해질 가능성이 큽니다.

최종 메모 - .NET에서 헝가리 표기법은 일반적으로 모범 사례로 간주되지 않습니다. 즉, dblGradesTotal5은 헝가리 표기법의 예입니다. 즉, 변수 이름 앞에 유형을 추가합니다. 간단한 gradesTotal5은 정상입니다.

+0

도움을 많이 주셔서 감사합니다. 나는 모든 코드를 업데이트했고 평균은 이제 완벽하게 작동합니다. ValidInput 함수가 작동하는 방법을 알아낼 수 없었습니다. 비록 이전에 작동 했었지만 코드 작성에 올바른 방법을 배우기를 원했기 때문에 피드백에 진심으로 감사했습니다. 공익 기능 ValidInput (ByVal 점수를 Double로) Double 점수가 = 0이고 점수가 100보다 작 으면 Return (점수) Else Return MessageBox.Show ("0-100 사이의 유효한 테스트 점수를 입력하십시오") 끝 부분 끝 기능 – cccstudent

+0

-1을 사용하려면 추가해야합니다. -1로 반환하고 -1로 추가했지만 두 경우 모두 값으로 사용하여 평균을 계산하는 데 사용했습니다. 그래서 -1을 사용하는 방법을 이해하지 못했거나 부적절한 데이터가 입력되었을 때 사용자에게 메시지 상자를 제공하는 숫자 범위 사이의 입력을 확인하기 위해 함수의 다른 부분을 사용해야하는지를 명확히해야합니다. – cccstudent

+0

@cccududent - 집에 도착하면 나중에 오늘 밤 살펴보고 대답 할 것입니다. – Tim