Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
хороший пример по созданию БД.doc
Скачиваний:
17
Добавлен:
13.05.2015
Размер:
1.02 Mб
Скачать

13. Задачи, решаемые в информационной системе

В техническом задании запланировано решение следующих задач:

  1. Вывод списков групп по запросам для одной группы и для всех групп.

  2. Вычисление среднего балла для каждого студента.

  3. Для каждой учебной группы вычисление количества студентов и среднего балла в группе.

Результаты решения задач оформляются в виде отчетов, вывод которых вызывается командами пункта меню «Отчеты» в строке меню главной формы.

Заметим, что первый пункт – это фактически два различных отчета: списки всех групп и список одной, указанной группы. Из-за этого мы при создании пунктов меню поставили в соответствие этому отчету два пункта меню: «Отчеты  Списки групп  Все группы» и «Отчеты  Списки групп  Одна группа».

Отчеты будем генерировать в виде текстовых файлов. Для их просмотра используем компонент RichTextBox.

Поместим этот элемент на форму frmMenu, задав ему следующие свойства:

Name = RichTextBox1

Системное имя

Font = Courier New

Шрифт

ReadOnly = True

Запрет редактирования

ScrollBars = Vertical

Вертикальная полоса прокрутки

Visible = False

Объект невидим

Кроме этого элемента поместим на форму еще и кнопку (Name = cmdSaveOtch, Visible = False), при нажатии которой будем сохранять просматриваемый отчет. Таким образом, макет формы frmMenu , доработанный для вывода результатов имеет вид, представленный на рисунке 8.

По нажатию кнопки «Сохранить отчет» текущий отчет (т.е. отчет, который просматривается в данный момент) должен быть сохранен. Таким образом, поскольку мы генерируем отчеты в текстовый файл с заранее заданным именем, то по нажатию кнопки должна быть сделана копия файла с отчетом.

Рисунок 8. Макет главной формы в режиме конструктора

Приведем код процедуры обработки события нажатия на кнопку «Сохранить отчет».

Private Sub cmdSaveOtch_Click(ByVal sender As System.Object,_

ByVal e As System.EventArgs) Handles cmdSaveOtch.Click

' запрос имени файла для сохранения

With SaveFileDialog1

.FileName = ""

.Filter = "Все файлы (*.*)|*.*|" + _

"Текстовые файлы. (*.txt)|*.txt|" + _

"Файлы исходных данных (*.dan)|*.dan|" + _

"Файлы результатов (*.rez)|*.rez"

.FilterIndex = 2

.ShowDialog()

End With

' если имя файла не пусто и не равно имени

' просматриваемого файла,

If SaveFileDialog1.FileName <> "" And _

richName <> SaveFileDialog1.FileName Then

' то производится копирование просматриваемого файла,

FileCopy(richName, SaveFileDialog1.FileName)

' его удаление

Kill(richName)

' и вывод в RichTextBox1 нового файла

richName = SaveFileDialog1.FileName

RichTextBox1.LoadFile(richName, _

RichTextBoxStreamType.PlainText)

' сообщение об успешном завершении сохранения отчета

MsgBox("Отчет сохранен", vbOKOnly + vbInformation, _

"Сохранение")

End If

End Sub

13.1. Вывод списков групп

Вывод списков групп реализован в процедуре обработки события выбора пункта меню «Отчеты  Списки групп  Все группы».

Прежде чем привести код этой процедуры, обсудим алгоритм, реализованный в ней. Идея алгоритма состоит в следующем: сначала файл с данными о студентах должен быть «отсортирован» по курсу, группе и фамилии; результатом чего станет индексный массив Ind, который позволит просматривать записи файла в отсортированном виде именно таким образом. Такая упорядоченность записей файла фактически представляет его разбитым на группы записей, самая внутренняя группа имеет одинаковые значения для курса и группы и упорядочена в алфавитном порядке фамилий. Поэтому в самом внешнем цикле перебираются курсы, во вложенном в него цикле перебираются номера групп, и в следующем по уровню вложенности цикле (для одинаковых значений курса и группы во всех записях) выбираются и выводятся в текстовый файл фамилии студентов. Код процедуры снабжен подробными комментариями.

Private Sub mnuQueryListAllItem_Click(ByVal sender As _

System.Object, ByVal e As System.EventArgs) _

Handles mnuQueryListAllItem.Click

Dim i As Integer

Dim Ind(Nmax) As Integer

Dim NK As Byte

Dim NG As Byte

Dim NPP As Integer

Dim KeyK(Nmax) As Single

Dim KeyG(Nmax) As Single

Dim KeyFIO(Nmax) As String

Dim R As TStud = New TStud()

' открывается временный вспомогательный файл otch.ist,

' находящийся в той же папке, что и работающий проект

Path2 = CurDir() + "\otch.txt"

F4 = FreeFile()

FileOpen(F4, Path2, OpenMode.Output)

' подготовка данных для сортировки по курсу, группе и ФИО

For i = 1 To N

R.ReadFromFile(f1, i)

KeyK(i) = R.Kurs

KeyG(i) = R.Group

KeyFIO(i) = R.FIO

Ind(i) = i

Next i

' сортировка данных

Call SortStr(KeyFIO, N, Ind)

Call Sort(KeyG, N, Ind)

Call Sort(KeyK, N, Ind)

' чтение первой записи в отсортированном списке

i = 1

R.ReadFromFile(f1, Ind(i))

Do While i <= N

' фиксирование и запись в файл номера текущего курса

NK = R.Kurs

PrintLine(F4, "Курс " + CStr(NK))

Do While NK = R.Kurs And i <= N

' фиксирование и запись в файл номера

' текущей группы

NG = R.Group

PrintLine(F4, vbTab + "Группа " + CStr(NG))

' порядковый номер студентов в группе

' начинается с единицы

NPP = 1

Do While NK = R.Kurs And NG = R.Group

' запись в файл ФИО студента

PrintLine(F4, vbTab + vbTab + CStr(NPP) + "." + _

vbTab + R.FIO)

NPP = NPP + 1

i = i + 1

' если еще есть записи, то считываем

' следующую, иначе выходим из цикла

If i <= N Then

R.ReadFromFile(f1, Ind(i))

Else

Exit Do

End If

Loop

' пропуск строки между списками различных групп

PrintLine(F4, "")

Loop

Loop

' файла отчета закрывается

FileClose(F4)

' загрузка только что созданного файла в RichTextBox1

RichTextBox1.LoadFile(Path2, _

RichTextBoxStreamType.PlainText)

richName = Path2

' показ элемента RichTextBox1 и кнопки «Сохранить отчет»

RichTextBox1.Visible = True

cmdSaveOtch.Visible = True

End Sub

Вывод списка одной группы реализован в процедуре обработки события выбора пункта меню «Отчеты  Списки групп  Одна группа»

В этой задаче у пользователя сначала запрашиваются значения для курса и группы, и проверяется корректность введенных значений. Затем файл исходных данных упорядочивается по полю «Фамилия» в алфавитном порядке; после чего он просматривается, из него выбираются и выводятся в текстовый файл записи, в которых значения курса и группы совпадают со значениями, введенными пользователем.

Private Sub mnuQueryListOneItem_Click(ByVal sender As _

System.Object, ByVal e As System.EventArgs) _

Handles mnuQueryListOneItem.Click

Dim i As Integer

Dim Ind(Nmax) As Integer

Dim NK As Byte

Dim NG As Byte

Dim NPP As Integer

Dim TempStr As String

Dim KeyFIO(Nmax) As String

Dim R As TStud = New TStud()

' открывается файл otch.ist, находящийся в той же папке,

' что и работающий проект

Path2 = CurDir() + "\otch.ist"

F4 = FreeFile()

FileOpen(F4, Path2, OpenMode.Output)

' запрос у пользователя интересующего его курса

TempStr = InputBox("Введите курс", "Ввод курса")

Do While Not IsNumeric(TempStr)

'если введенный курс не является числом,

' но является пустым значением

If (TempStr = "") Then

' то файл закрывается и осуществляется выход

' из процедуры

FileClose(F4)

Exit Sub

End If

' если введенный курс не является числом,

' то еще раз производится запрос номера курса

MsgBox("Курс - число", vbOKOnly + vbExclamation, _

"Ошибка")

TempStr = InputBox("Введите курс", "Ввод курса")

Loop

' перевод введенного курса в числовое значение

NK = CByte(TempStr)

' запрос у пользователя интересующей его группы

TempStr = InputBox("Введите группу", "Ввод группы")

Do While Not IsNumeric(TempStr)

'если введенная группа не является числом,

' но является пустым значением

If (TempStr = "") Then

' то файл закрывается и осуществляется выход

' из процедуры

FileClose(F4)

Exit Sub

End If

' если введенная группа не является числом,

' то еще раз производится запрос номера группы

MsgBox("Группа-число", vbOKOnly + vbExclamation, _

"Ошибка")

TempStr = InputBox("Введите группу", "Ввод группы")

Loop

' перевод введенной группы в числовое значение

NG = CByte(TempStr)

' подготовка данных для сортировки по полю ФИО

For i = 1 To N

R.ReadFromFile(f1, i)

KeyFIO(i) = R.FIO

Ind(i) = i

Next i

' сортировка данных

Call SortStr(KeyFIO, N, Ind)

' запись в файл информации о курсе и группы

PrintLine(F4, "Курс " + CStr(NK) + ", Группа " + CStr(NG))

' порядковый номер студентов в группе

' начинается с единицы

NPP = 1

For i = 1 To N

' считывание следующей записи и если курс и группа

' соответствуют, то производится вывод в файл отчета

R.ReadFromFile(f1, Ind(i))

If R.Kurs = NK And R.Group = NG Then

PrintLine(F4, vbTab + CStr(NPP) + "." + vbTab + R.FIO)

NPP = NPP + 1

End If

Next i

' файл отчета закрывается

FileClose(F4)

' загрузка только что созданного файла в RichTextBox1

RichTextBox1.LoadFile(Path2, _

RichTextBoxStreamType.PlainText)

richName = Path2

' показ элемента RichTextBox1 и кнопки «Сохранить отчет»

RichTextBox1.Visible = True

cmdSaveOtch.Visible = True

End Sub

13.2. Количество студентов и средний балл в группах

Во второй и третьей задаче из числа запланированных задач необходимо для каждого студента вычислить средний балл. Вынесем вычисление среднего балла каждого студента в отдельную пользовательскую процедуру, которая будет принадлежать форме frmMenu. В этой процедуре создается вспомогательный файл прямого доступа с записями пользовательского типа Tball, содержащий столько же записей, сколько находится в файле исходных данных. Пользовательский тип Tball содержит поле для вычисления среднего балла. Код процедуры приведен ниже.

Private Sub AverageBallCreate()

Dim i As Integer

Dim j As Integer

Dim KeyK(Nmax) As Single

Dim KeyG(Nmax) As Single

Dim KeyFIO(Nmax) As String

Dim KeyB(Nmax) As Single

Dim R As TStud = New TStud()

Dim S As TBall = New TBall()

' открывается вспомогательный файл Ball.avg, находящийся в

' той же папке, что и работающий проект

Path1 = CurDir + "\Ball.avg"

F3 = New FileStream(Path1, FileMode.Create)

' читается следующая запись из основного файла базы данных

' вычисляется средний балл и созданная запись о среднем

' балле выводится во вспомогательный файл

For i = 1 To N

R.ReadFromFile(f1, i)

S.Sb = 0

For j = 1 To R.Kol

S.Sb = S.Sb + R.M(j - 1)

Next j

S.Sb = S.Sb / R.Kol

S.Kurs = R.Kurs

S.Group = R.Group

S.FIO = R.FIO

S.writeToFile(F3, i)

Next i

' вспомогательный файл закрывается

F3.Close()

End Sub

Вычисление количества студентов и среднего балла для каждой учебной группы реализовано в процедуре обработки события выбора команды меню «Отчеты  Количество и средний балл».

В файле исходных данных содержатся только оценки, поэтому в этой процедуре, сначала формируется вспомогательный файл с данными о студентах (курс, группа, ФИО, средний балл). Затем вспомогательный файл упорядочивается по курсу и группе. После этого вычисляется количество записей в группе с одинаковыми значениями курса и группы, а также средний балл в этой же группе.

Алгоритм вычислений похож на алгоритм, используемый для вывода списков по группам. Во внешнем цикле перебираются курсы, во вложенном в него цикле перебираются номера групп, и в следующем по уровню вложенности цикле (для одинаковых значений курса и группы во всех записях) увеличиваются значения счетчика для количества студентов и суммы для накопления средних баллов. Значения счетчика и суммы обнуляются перед входом во внутренний цикл, после выхода из которого выводится количество студентов в группе и вычисляется и выводится средний балл в группе. Код процедуры снабжен подробными комментариями.

Private Sub mnuQueryKolItem_Click(ByVal sender As _

System.Object, ByVal e As System.EventArgs) _

Handles mnuQueryBallItem.Click

Dim Sum As Double

Dim k As Integer

Dim i As Integer

Dim Ind(Nmax) As Integer

Dim KeyK(Nmax) As Single

Dim KeyG(Nmax) As Single

Dim NK As Byte

Dim NG As Byte

Dim S As TBall = New TBall()

' вызов процедуры создания вспомогательного файла,

' содержащего информацию о среднем балле каждого студента

AverageBallCreate()

' открывается созданный вспомогательный файл

F3 = New FileStream(Path1, FileMode.Open)

' открывается вспомогательный файл kol.avg, находящийся в

' той же папке, что и работающий проект

Path2 = CurDir() + "\kol.avg"

F4 = FreeFile()

FileOpen(F4, Path2, OpenMode.Output)

' подготовка данных для сортировки по курсу и группе

For i = 1 To N

S.ReadFromFile(F3, i)

KeyK(i) = S.Kurs

KeyG(i) = S.Group

Ind(i) = i

Next i

' сортировка данных

Call Sort(KeyG, N, Ind)

Call Sort(KeyK, N, Ind)

' вывод заголовка таблицы отчета

PrintLine(F4, "Курс" + vbTab + "Группа" + vbTab + _

"Кол-во студ." + vbTab + "Сред-ний балл")

' чтение первой записи в отсортированном списке

i = 1

S.ReadFromFile(F3, Ind(i))

Do While i <= N

' фиксирование номера текущего курса

NK = S.Kurs

Do While NK = S.Kurs And i <= N

' фиксирование номера текущей группы

NG = S.Group

' начальные количество и сумма равны нулю

k = 0

Sum = 0

' вычисление количества студентов и суммы их

' средних баллов

Do While NK = S.Kurs And NG = S.Group

k = k + 1

Sum = Sum + S.Sb

i = i + 1

If i <= N Then

S.ReadFromFile(F3, Ind(i))

Else

Exit Do

End If

Loop

' вывод в файл номера курса, номера группы,

' количества студентов и среднего балла группы

PrintLine(F4, CStr(NK) + vbTab + CStr(NG) + vbTab _

+ vbTab + vbTab + CStr(k) + vbTab + vbTab _

+ vbTab + CStr(Format(Sum / k, "#0.00")))

Loop

Loop

' вспомогательные файлы закрываются

F3.Close()

FileClose(F4)

' загрузка только что созданного файла в RichTextBox1

RichTextBox1.LoadFile(Path2, _

RichTextBoxStreamType.PlainText)

richName = Path2

' показ элемента RichTextBox1 и кнопки «Сохранить отчет»

RichTextBox1.Visible = True

cmdSaveOtch.Visible = True

End Sub

13.3. Вычисление среднего балла для каждого студента

Вычисление среднего балла для каждого студента реализовано в процедуре обработки события выбора команды меню «Отчеты  Вычисление среднего балла».

Собственно вычисление среднего балла алгоритмически не является трудной задачей, и она уже решена в пользовательской процедуре. В процедуре для данной команды меню будет использована эта процедура. Для вывода результата будем использовать таблицу (элемент DataGridView) , для этого добавим в проект еще одну форму, на которую поместим элемент DataGridView и кнопку, для того чтобы дать возможность пользователю не только просмотреть таблицу на экране, но и сохранить результаты в текстовом файле для дальнейшего использования.

Добавим в проект форму, дадим форме имя frmTableRez и поместим на нее элемент для отображения данных в виде таблицы (DataGridView), переименуем этот элемент, задав его имя, GridView1.

Также поместим на форму кнопку с системным именем cmdSaveOtch для сохранения отчета в виде текстового файла.

Процедура обработки события нажатия на кнопку «Сохранить отчет» имеет вид:

Private Sub cmdSaveOtch_Click(ByVal sender As System.Object, _

ByVal e As System.EventArgs) Handles cmdSaveOtch.Click

Dim i As Integer

Dim j As Integer

' запрос имени файла для сохранения отчета

With frmMenu.SaveFileDialog1

.FileName = ""

.Filter = "Все файлы (*.*)|*.*|" + _

"Текстовые файлы. (*.txt)|*.txt|" + _

"Файлы исходных данных (*.dan)|*.dan|" + _

"Файлы результатов (*.rez)|*.rez"

.FilterIndex = 2

.ShowDialog()

End With

' если имя файла не пусто,

If frmMenu.SaveFileDialog1.FileName <> "" Then

' то файл открывается

F4 = FreeFile()

FileOpen(f4, frmMenu.SaveFileDialog1.FileName, _

OpenMode.Output)

' и в него выводятся все ячейки таблицы

With GridView1

For i = 0 To .ColumnCount - 1

Print(F4, .Columns(i).Name + vbTab)

Next i

PrintLine(F4, "")

For j = 0 To .RowCount - 1

For i = 0 To .ColumnCount - 1

Print(F4, CStr(.Rows(j).Cells(i).Value) + vbTab)

Next i

PrintLine(F4, "")

Next j

End With

' файл отчета закрывается

FileClose(F4)

' сообщение об успешном завершении сохранения отчета

MsgBox("Отчет сохранен", vbOKOnly + vbInformation, _

"Сохранение")

End If

End Sub

А теперь приведем код процедуры обработки события, соответствующего выбору пункта меню «Отчеты  Вычисление среднего балла». В этой процедуре предусмотрены две возможности вывода результатов: в виде, упорядоченном по курсу, группе и фамилиям студентов; или в виде, упорядоченном по курсу, группе и убыванию среднего балла. Код процедуры снабжен подробными комментариями.

Private Sub mnuQueryBallItem_Click(ByVal sender As _

System.Object, ByVal e As System.EventArgs) _

Handles mnuQueryKolItem.Click

Dim i As Integer

Dim Ind(Nmax) As Integer

Dim KeyK(Nmax) As Single

Dim KeyG(Nmax) As Single

Dim KeyFIO(Nmax) As String

Dim KeyB(Nmax) As Single

Dim S As TBall = New TBall()

Dim Button As Integer

' вызов процедуры создания вспомогательного файла,

' содержащего информацию о среднем балле каждого студента

AverageBallCreate()

' открывается созданный вспомогательный файл

F3 = New FileStream(Path1, FileMode.Open)

' подготовка данных для сортировок

For i = 1 To N

S.ReadFromFile(F3, i)

KeyK(i) = S.Kurs

KeyG(i) = S.Group

KeyFIO(i) = S.FIO

KeyB(i) = -S.Sb ' для сортировки по убыванию

Ind(i) = i

Next i

' запрос о порядке вывода отчета

Button = MsgBox("Вывод по убыванию среднего балла?", _

vbQuestion + vbYesNo, "Вывод результата")

' сортировка данных производится по курсу, группе и либо по

' ФИО, либо по среднему баллу, в зависимости ответа

' пользователя на запрос

If Button = vbYes Then

Call Sort(KeyB, N, Ind)

Call Sort(KeyG, N, Ind)

Call Sort(KeyK, N, Ind)

Else

Call SortStr(KeyFIO, N, Ind)

Call Sort(KeyG, N, Ind)

Call Sort(KeyK, N, Ind)

End If

' заполнение заголовка формы frmTableRez

frmTableRez.Text = "Просмотр файла: " + Path1

With frmTableRez.GridView1

.ColumnCount = 5

' запись названий столбцов в таблицу

.Columns(0).Name = "№"

.Columns(1).Name = "Курс"

.Columns(2).Name = "Группа"

.Columns(3).Name = "Фамилия И.О."

.Columns(4).Name = "Средний балл"

' чтение очередной записи и загрузка ее полей

' в таблицу

For i = 1 To N

S.ReadFromFile(F3, Ind(i))

' загрузка новой строки в таблицу

Dim row As String() = New String() _

{CStr(i), S.Kurs, S.Group, S.FIO, _

CStr(Format(S.Sb, "#0.00"))}

.Rows.Add(row)

Next i

End With

' вспомогательный файл закрывается

F3.Close()

' загрузка формы frmTableRez

frmTableRez.Show()

End Sub

Таким образом, нами были предусмотрены все средства, запланированные в техническом задании проекта, а значит, информационная система «Студенты» после прохождения комплекса разнообразных тестов на работоспособность и корректность обработки информации может быть внедрена на рабочем месте заказчика.