- •Курсовая работа
- •Оглавление
- •Глава 1. Введение 3
- •Глава 2. Теоретические сведения по системам счисления 5
- •Глава 3. Практическая часть 21
- •Введение
- •Теоретические сведения по системам счисления
- •История развития систем счисления
- •Теоретические основы систем счисления
- •Информационные системы счисления
- •Практическая часть
- •Разработка проекта
- •Программная реализация
- •Заключение
- •Список источников
- •Приложения Приложение 1
- •Приложение 2
-
Программная реализация
Итак, перейдем к реализации программы.
За главное окно отвечает модуль MainForm. Для упрощения кода и наглядности для данных используется отдельная структура. Для получения пути к файлам используются компоненты OpenFileDialog и SaveFileDialog, так как они обладают наибольшей простотой. При их создании используется конструктор.
Для обработки ошибок открытия файлов используется оператор try, который дает возможность опускать проверку каждой строки для больших фрагментов кода.
С помощью процедуры Update() мы сразу загружаем в память ресурсы нужные для работы компонента WebBrowser. Благодаря этому убирается “зависание” при первом открытии формы Reader.
Код модуля приведен в листинге 1.
-
Модуль MainForm
'Для работы с файлами нам потребуется импортировать следующий модуль
Imports System.IO
Public Class MainForm
'Объявляем запись, в которой будут хранится все данные программы
Structure TData
'Информация для тестирования
Structure TDataTest
Enum TQuestionType 'Для отображения вопросов используется:
std = 0 'текстовое поле и изображение
End Enum
Structure TQuestion 'Один вопрос программно это:
Dim Question As String 'текст
Dim Type As TQuestionType 'тип вопроса
Dim Answers As String() 'массив вопросов
Dim Opt As String() 'массив дополнительных опций
Dim Ball As Double 'балл за вопрос
Dim Image As Bitmap 'рисунок
End Structure
Dim Name, Desc As String 'Название и информация для теста
Dim nQ, Time As Integer 'Кол-во вопросов и время для теста
Dim Questions As TQuestion() 'Массив вопросов
End Structure
'Далее описание теоретической базы
Structure TDataTheory
Dim Title, Desc As String 'Название и информация
Dim FilePath As String 'Путь к корневому файлу .html
Dim Weight As String 'Объем
End Structure
'Описание статистики
Structure TStat
Dim Right, Wrong, NoTime, Time As Integer
Dim balls As Double
Dim TestName, Student As String
End Structure
Dim Stat As TStat
Dim Test As TDataTest
Dim Theory As TDataTheory
End Structure
'Объявление переменных
Public Data As TData
'Функция, которая возвращает true в случае успешного открытия файла. В качестве параметра type передается тип открываемого файла. “0” – файл “.test”, “1” – файл “.theory”, “2” – файл “.stat”
Private Function OpenFile(ByVal f As String, ByVal type As Integer) As Boolean
Dim fFile As FileStream 'универсальный файловый дескриптор
Dim Reader As StreamReader 'инструмент для чтения файла
Dim Backup As TData 'в случае ошибки возвращает нач. значения
Dim Flag As String 'флаг, используемый в циклах
Backup = Data
OpenFile = True
Try 'ручное управление обработкой ошибок
If type = 0 Then 'открываем файл “.test”
fFile = New FileStream(f, FileMode.Open)
Reader = New StreamReader(fFile)
ReDim Data.Test.Questions(0 To 0) 'считываем информацию
Data.Test.Name = Reader.ReadLine
Data.Test.Desc = Reader.ReadLine
Data.Test.Time = Val(Reader.ReadLine)
While Not (Reader.EndOfStream)
Data.Test.Questions(Data.Test.Questions.Length - 1).Question = Reader.ReadLine.Replace("|", Chr(13))
Data.Test.Questions(Data.Test.Questions.Length - 1).Answers = Reader.ReadLine.Split("|")
Data.Test.Questions(Data.Test.Questions.Length - 1).Type = Val(Reader.ReadLine)
Flag = Reader.ReadLine
If Flag <> "*" Then
Data.Test.Questions(Data.Test.Questions.Length - 1).Image = Image.FromFile(BDir + Flag)
End If
Data.Test.Questions(Data.Test.Questions.Length - 1).Ball = Val(Reader.ReadLine)
Data.Test.Questions(Data.Test.Questions.Length - 1).Opt = Reader.ReadLine.Split("|")
If Data.Test.Questions(Data.Test.Questions.Length - 1).Opt(0) = "*" Then
Data.Test.Questions(Data.Test.Questions.Length - 1).Opt = Nothing
End If
‘лишний элемент в массиве нужно удалить
If Not (Reader.EndOfStream) Then
ReDim Preserve Data.Test.Questions(0 To Data.Test.Questions.Length)
End If
End While
ElseIf type = 1 Then 'открываем файл “.theory”
fFile = New FileStream(f, FileMode.Open)
Reader = New StreamReader(fFile)
Data.Theory.Title = Reader.ReadLine
Data.Theory.Desc = Reader.ReadLine
Data.Theory.Weight = Reader.ReadLine
Data.Theory.FilePath = BDir + Reader.ReadLine
ElseIf type = 2 Then 'открываем файл “.stat”
fFile = New FileStream(f, FileMode.Open)
Reader = New StreamReader(fFile)
Data.Stat.TestName = Reader.ReadLine
Data.Stat.Student = Reader.ReadLine
Data.Stat.Wrong = Reader.ReadLine
Data.Stat.Right = Reader.ReadLine
Data.Stat.NoTime = Reader.ReadLine
Data.Stat.Time = Reader.ReadLine
Data.Stat.balls = Reader.ReadLine
End If
fFile.Close()
Reader.Close()
Catch
'В случае ошибки закрываем дескрипторы, возвращаем все на свои места.
Data = Backup
OpenFile = False
fFile.Close()
Reader.Close()
End Try
End Function
'Кнопка “Загрузить тест”
Private Sub Button5_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button5.Click
OpenFileDialog.Reset()
OpenFileDialog.Filter = "Тестовые задания|*.test"
OpenFileDialog.ShowDialog()
If OpenFileDialog.FileName = "" Then
Exit Sub
End If
If OpenFile(OpenFileDialog.FileName, 0) Then
Label3.Text = "Название теста:" + Chr(13) + Data.Test.Name + Chr(13)
Label3.Text += "Описание теста:" + Chr(13) + Data.Test.Desc + Chr(13)
Label3.Text += "Количество вопросов:" + Data.Test.Questions.Length.ToString + Chr(13)
Button1.Enabled = True
Else
MessageBox.Show("Ошибка открытия файла.", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error)
End If
Button1.Focus()
End Sub
'Кнопка “Загрузить теорию”
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
OpenFileDialog.Reset()
OpenFileDialog.Filter = "Документы|*.theory"
OpenFileDialog.ShowDialog()
If OpenFileDialog.FileName = "" Then
Exit Sub
End If
If OpenFile(OpenFileDialog.FileName, 1) Then
Label2.Text = "Название:" + Chr(13) + Data.Theory.Title + Chr(13)
Label2.Text += "Описание:" + Chr(13) + Data.Theory.Desc + Chr(13)
Label2.Text += "Объем:" + Data.Theory.Weight.ToString
Button6.Enabled = True
Else
MessageBox.Show("Ошибка открытия файла.", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error)
End If
Button6.Focus()
End Sub
'Процедура отображения результатов тестирования
Sub ShowStat()
Label1.Text = "Название теста:" + Chr(13) + Data.Stat.TestName + Chr(13)
Label1.Text += "Студент:" + Chr(13) + Data.Stat.Student + Chr(13)
Label1.Text += "Всего вопросов: " + (Data.Stat.Right + Data.Stat.Wrong + Data.Stat.NoTime).ToString + Chr(13)
Label1.Text += "Верно: " + Data.Stat.Right.ToString + Chr(13)
Label1.Text += "Неверно: " + Data.Stat.Wrong.ToString + Chr(13)
Label1.Text += "Без ответа: " + Data.Stat.NoTime.ToString + Chr(13)
Label1.Text += "Коэффициент: " + (Math.Round(Data.Stat.Right / (Data.Stat.Right + Data.Stat.Wrong + Data.Stat.NoTime), 2) * 100).ToString + "%" + Chr(13)
Label1.Text += "Затраченное время: " + Math.Truncate(Data.Stat.Time / 60).ToString + " м. " + (Data.Stat.Time Mod 60).ToString + " с." + Chr(13)
Label1.Text += "Оценка: " + Math.Round(Data.Stat.balls).ToString + Chr(13)
End Sub
'Кнопка “Начать тестирование”
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Test.Show()
Me.Visible = False
End Sub
'Кнопка “Читать теорию”
Private Sub Button6_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button6.Click
Reader.Show()
Me.Visible = False
End Sub
'Загрузка формы
Private Sub MainForm_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Reader.Update() 'данный код позволяет предварительно загрузить библиотеки для работы компонента WebBrowser
End Sub
'Кнопка “Сохранить результаты”
Private Sub Button4_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button4.Click
Dim dlg As SaveFileDialog = New SaveFileDialog()
dlg.CheckPathExists = True
dlg.AddExtension = True
dlg.Filter = "Результаты|*.stat"
'dlg.FileName = TimeOfDay.ToString.Replace(".", "-").Replace(" ", "_").Replace(":", "-") + ".stat"
dlg.FileName = TimeOfDay.Ticks.ToString + "_" + Data.Stat.Student + "_" + ".stat"
Dim res As DialogResult = dlg.ShowDialog()
If res = Windows.Forms.DialogResult.Cancel Then
Exit Sub
End If
Dim f As FileStream
f = New FileStream(dlg.FileName, FileMode.CreateNew)
Dim stw As IO.StreamWriter
stw = New IO.StreamWriter(f)
stw.WriteLine(Data.Stat.TestName)
stw.WriteLine(Data.Stat.Student)
stw.WriteLine(Data.Stat.Wrong)
stw.WriteLine(Data.Stat.Right)
stw.WriteLine(Data.Stat.NoTime)
stw.WriteLine(Data.Stat.Time)
stw.WriteLine(Data.Stat.balls)
stw.Close()
f.Close()
End Sub
'Кнопка “Просмотреть результаты”
Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
OpenFileDialog.Reset()
OpenFileDialog.Filter = "Результаты|*.stat"
OpenFileDialog.ShowDialog()
If OpenFileDialog.FileName = "" Then
Exit Sub
End If
If OpenFile(OpenFileDialog.FileName, 2) Then
ShowStat()
Else
MessageBox.Show("Ошибка открытия файла.", "Ошибка", MessageBoxButtons.OK, MessageBoxIcon.Error)
End If
Button1.Focus()
End Sub
End Class
Далее, для модуля Reader используется компонент WebBrowser, который обладает большими преимуществами в отношении просмотра контента, если учесть, что все отображение документов он, буквально, берет на себя. Нам лишь остается вызвать команды встроенные в его класс. Поэтому он используется в модуле (листинг 2). Код модуля приведен в листинге 2.
-
Модуль Reader
Public Class Reader
'Загрузка формы
Private Sub Reader_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Me.Text = MainForm.Data.Theory.Title
WebBrowser1.Navigate(MainForm.Data.Theory.FilePath)
End Sub
'Закрытие формы
Private Sub Reader_FormClosed(ByVal sender As System.Object, ByVal e As System.Windows.Forms.FormClosedEventArgs) Handles MyBase.FormClosed
If Test.Visible <> True Then
MainForm.Visible = True
End If
End Sub
'Кнопка “начать тестирование”
Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
Test.Show()
Me.Close()
End Sub
'Кнопка “закончить”
Private Sub Button4_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button4.Click
Me.Close()
End Sub
'Кнопка “Главная”
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
WebBrowser1.Navigate(MainForm.Data.Theory.FilePath)
End Sub
'Кнопка “Назад”
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
WebBrowser1.GoBack()
End Sub
'Для большей “встроенности” компонента фоновый цвет документа делается таким же как на форме
Private Sub WebBrowser1_DocumentCompleted(ByVal sender As System.Object, ByVal e As System.Windows.Forms.WebBrowserDocumentCompletedEventArgs) Handles WebBrowser1.DocumentCompleted
WebBrowser1.Document.BackColor = MainForm.BackColor
End Sub
End Class
В модуле Test структура TBase используется для хранения элементов размещенных на форме. Обращаясь к переменной Base, производной от TBase, мы можем динамически их изменять. Процедура Clear_Base() используется для очистки значений занесенных в переменную, а в процедуре Show_Q() как раз реализовано динамическое размещение элементов на форме..
Для удобства, программа сделана так, что пройти тестирование можно при помощи лишь одной клавиатуры. Для этого используется обработка нажатия клавиши Enter и метод Focus(). Также используется шрифт размера 14pt, вместо стандартного 12pt, что позволяет быстрее прочитать и понять вопрос.
Можно выводить не только текстовую информацию, но также в дополнительном изображении можно представить любую формулу, таблицу, рисунок и т. п.
Из особенностей программы можно отметить, что она использует так называемую “очередь вопросов”, что позволяет отправлять пропущенные вопросы в конец и не заботиться о порядке их следования. Код модуля приведен в листинге 3.
-
Модуль Test
Public Class Test
Dim Turn As Integer() 'порядок вопросов
Dim Current As Integer = 0 'текущий вопрос
Dim LastTime As Integer 'оставшееся время
Dim CAnswers As String() 'ответы
Dim f As Boolean = True 'флаг
Structure TBase 'используется для генерации
Dim qLabel As Label() 'динамического отображения вопросов
Dim qImage As PictureBox()
Dim qRadio As RadioButton()
End Structure
Dim Base As TBase
'Очищает окно
Private Sub Clear_Base(ByRef first As Boolean)
If Not (first) Then
For Each i In Base.qImage
Me.Controls.Remove(i)
Next
For Each i In Base.qRadio
Me.Controls.Remove(i)
Next
For Each i In Base.qLabel
Me.Controls.Remove(i)
Next
End If
ReDim Base.qImage(0 To 0)
ReDim Base.qLabel(0 To 0)
ReDim Base.qRadio(0 To 0)
End Sub
'Обновление информационного поля
Private Sub Reflesh_Info()
Info.Text = "Осталось вопросов: " + (Turn.Length - Current - 2).ToString + "; Осталось времени: " + (Math.Truncate(LastTime / 60)).ToString + " м. " + (LastTime Mod 60).ToString + " с."
End Sub
'Процедура, отображающая вопрос
Private Sub Show_Q(ByVal nQ As Integer)
Const border = 10 'граница, вдоль которой расположены элементы
Clear_Base(False)
'если тип вопроса “std”, то выводим одно label и picture box
If MainForm.Data.Test.Questions(nQ).Type = MainForm.TData.TDataTest.TQuestionType.std Then
Base.qLabel(0) = New Label
Me.Controls.Add(Base.qLabel(0))
Base.qLabel(0).Top = border
Base.qLabel(0).Left = border
Base.qLabel(0).Text = MainForm.Data.Test.Questions(nQ).Question
Base.qLabel(0).Width = Me.Width - border * 2 - 5
Base.qLabel(0).Height = 380
Base.qLabel(0).Font = New Font(Me.Font.FontFamily, 14, FontStyle.Regular)
If Not (MainForm.Data.Test.Questions(nQ).Image Is Nothing) Then
Base.qImage(0) = New PictureBox
Me.Controls.Add(Base.qImage(0))
Base.qImage(0).BackColor = Color.Transparent
Base.qImage(0).Image = MainForm.Data.Test.Questions(nQ).Image
Base.qImage(0).Width = Base.qLabel(0).Width
Base.qLabel(0).SendToBack()
Base.qImage(0).Left = Base.qLabel(0).Left + 1
Base.qImage(0).Height = 200
Base.qImage(0).Top = Base.qLabel(0).Top + Graphics.FromHwnd(Base.qLabel(0).Handle).MeasureString(MainForm.Data.Test.Questions(nQ).Question, Base.qLabel(0).Font, Base.qLabel(0).Width).Height
Base.qImage(0).Visible = True
End If
End If
'Подведение статистики. В st передается ФИО студента и номер группы
Private Sub Collect_Info(ByVal st As String)
Dim i As Integer
Dim helpa As String()
'Очищаем предыдущую статистику
MainForm.Data.Stat.Right = 0
MainForm.Data.Stat.Wrong = 0
MainForm.Data.Stat.NoTime = 0
MainForm.Data.Stat.balls = 0
MainForm.Data.Stat.Student = st
MainForm.Data.Stat.TestName = MainForm.Data.Test.Name
MainForm.Data.Stat.Time = MainForm.Data.Test.Time – LastTime
'Сверяем ответы
For i = 0 To CAnswers.Length - 1
ReDim helpa(0 To MainForm.Data.Test.Questions(i).Answers.Length)
helpa = MainForm.Data.Test.Questions(i).Answers
If (MainForm.Data.Test.Questions(i).Answers(0) = CAnswers(i)) Or (Array.IndexOf(MainForm.Data.Test.Questions(i).Answers, CAnswers(i)) > 0) Then
MainForm.Data.Stat.Right += 1
MainForm.Data.Stat.balls += MainForm.Data.Test.Questions(i).Ball
Else
MainForm.Data.Stat.Wrong += 1
End If
Next i
'Подсчитываем время
MainForm.Data.Stat.NoTime = MainForm.Data.Test.Questions.Length - MainForm.Data.Stat.Right - MainForm.Data.Stat.Wrong
End Sub
'Загрузка формы, где производится задание начальных значений
Private Sub Test_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Dim i As Integer
ReDim Turn(0 To 0)
For i = 0 To MainForm.Data.Test.Questions.Length - 1
Turn(i) = i
ReDim Preserve Turn(0 To Turn.Length)
Next i
ReDim CAnswers(0 To Turn.Length - 2)
Clear_Base(True)
Text = MainForm.Data.Test.Name
LastTime = MainForm.Data.Test.Time
Reflesh_Info()
Show_Q(Turn(Current))
TextBox1.SelectAll()
Timer1.Enabled = True
End Sub
'Нажатие кнопки “Пропустить”
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Turn(Turn.Length - 1) = Turn(Current)
ReDim Preserve Turn(0 To Turn.Length)
Current += 1
Show_Q(Turn(Current))
End Sub
'Процедура завершения теста. В качестве параметра abort передается значение, прошел ли студент тестирование или решил его прервать
Private Sub End_Test(ByVal abort As Boolean)
Timer1.Enabled = False
If abort Then
MainForm.Visible = True
Me.Close()
Exit Sub
End If
Dim st As String
Do
st = InputBox("Введите ФИО и номер группы", "Вы завершили тест!", "")
Loop Until st <> ""
Collect_Info(st)
MainForm.Visible = True
MainForm.ShowStat()
MainForm.Button4.Enabled = True
MainForm.Button4.Focus()
Me.Close()
End Sub
'Нажатие на кнопку “Ответить”
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
CAnswers(Turn(Current)) = TextBox1.Text
If Current <> Turn.Length - 2 Then
TextBox1.Text = "Введите ответ"
TextBox1.Focus()
TextBox1.SelectAll()
Current += 1
Show_Q(Turn(Current))
Reflesh_Info()
If Current = Turn.Length - 2 Then
Button1.Enabled = False
End If
Else
End_Test(False)
End If
End Sub
'Отсчет времени. После того как LastTime окажется равным 0, тест завершается
Private Sub Timer1_Tick(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Timer1.Tick
If f Then 'первый запуск таймера
TextBox1.Focus()
TextBox1.SelectAll()
Timer1.Interval = 1000
f = False
End If
LastTime -= 1
Reflesh_Info()
If LastTime = 0 Then
End_Test(False)
End If
End Sub
'Нажатие на кнопку “Завершить тест”
Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
If MessageBox.Show("Вы уверены, что хотите завершить тест?", "Внимание!", MessageBoxButtons.YesNo) = Windows.Forms.DialogResult.Yes Then
End_Test(True)
End If
End Sub
'Если в текстовом поле нажимается клавиша Enter, то считывается ответ
Private Sub TextBox1_KeyPress(ByVal sender As System.Object, ByVal e As System.Windows.Forms.KeyPressEventArgs) Handles TextBox1.KeyPress
If Chr(13) = e.KeyChar Then
Button2_Click(Button2, e)
e.Handled = True
End If
End Sub
End Class