Что значит факт…???

Самый интересный и полезный справочник ответов на вопрос "Что значит"?

Статьи

язык программирования и среда программирования в чем разница

Языки и системы программирования

Описание презентации по отдельным слайдам:

Языки и системы программирования

Современные системы программирования включают в себя: Транслятор (компилятор или интерпретатор) Интегрированную среду разработки программ Встроенный текстовый редактор Библиотеки стандартных программ и функций Средства отладки программ Встроенные справочные службы и т.д.

Компиляция – многоступенчатый процесс, включающий этапы: Синтаксический анализ – проверка правильности конструкций, использованных в тексте программы Семантический анализ – выявление несоответствий типов и структур переменных, функций и процедур Генерация объектного кода – завершающий этап трансляции.

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

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

2. Исходный код преобразуют в инструкции процессора. Это преобразование выполняют специальные программы-переводчики (трансляторы).

Турбо Паскаль появился на рынке программных продуктов в 1984 году. Турбо Паскаль состоит из языка программирования и среды программирования, которая создаёт удобства в работе. Из истории

В 1992 году вышла 7 версия Турбо Паскаля. Пакет Turbo Pascal 7.0 использует новейшие (на тот период) достижения в программировании. Он может быть использован на любой машине. Эта версия снабжена большим количеством стандартных библиотек.

Включает: текстовый редактор компилятор компоновщик загрузчик Запускается: Программой TURBO.EXE Интегрированная среда программирования Turbo Pascal

Строка заголовка Строка меню Рабочая область Строка подсказки

Курс повышения квалификации

Охрана труда

Курс профессиональной переподготовки

Библиотечно-библиографические и информационные знания в педагогическом процессе

Курс профессиональной переподготовки

Охрана труда

Ищем педагогов в команду «Инфоурок»

Номер материала: ДВ-227360

Не нашли то что искали?

Вам будут интересны эти курсы:

Оставьте свой комментарий

Авторизуйтесь, чтобы задавать вопросы.

Безлимитный доступ к занятиям с онлайн-репетиторами

Выгоднее, чем оплачивать каждое занятие отдельно

В России предложили учредить День семейного волонтерства

Время чтения: 2 минуты

Путин поручил не считать выплаты за классное руководство в средней зарплате

Время чтения: 1 минута

Минобрнауки обновит перечень специальностей высшего образования

Время чтения: 1 минута

В России утверждены новые аккредитационные показатели для школ и колледжей

Время чтения: 2 минуты

Учителям предлагают 1,5 миллиона рублей за переезд в Златоуст

Время чтения: 1 минута

В Ленобласти педагоги призеров и победителей олимпиады получат денежные поощрения

Время чтения: 1 минута

Подарочные сертификаты

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

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

Источник

Языки и среды программирования.

Языки и среды программирования.

АЛГОРИТМЫ.

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

Способы записи алгоритмов:

Базовые структуры алгоритмов:

ЯЗЫКИ И СИСТЕМЫ ПРОГРАММРОВАНИЯ.

Способы описания ЯП.

Для описания ЯП используются две системы описания:

Нотация Бэкуса содержит конструкцию следующего вида:

Левая часть определения конструкций языка содержит наименование определяемого элемента, взятого в угловые скобки.

Правая часть включает совокупность элементов, соединённых знаком |, которая трактуется как «или» и объединяет альтернативы – различные варианты значения, определяемого элемента. Части соединяются оператором ::=, который может трактоваться, как является по определению.

Нотация IBM включает следующие элементы:

означает обязательное присутствие одного из

Рекурсивное определение в IBM-нотации не используются.

СИСТЕМЫ ПРОГРАММИРОВАНИЯ.

Система программирования (СП) является инструментальным средством программиста – разработка системных или прикладных программ. Первоначально, в ранних ОС, системы программирования входили в состав ОС и были доступны только «избранным».

Широкое распространение ПЭВМ и доступность СП привели к приобщению широких кругов пользователей к увлекательному занятию – написанию собственных программ в самых различных средах.

Современные СП обычно предоставляют пользователям такие средства разработки программ, как:

· Создание и редактирование текстов программ;

· Компилятор или интерпретатор;

· Библиотеки стандартных процедур и функций;

· Утилиты (вспомогательные рабочие программы);

· Отладчик (средство, помогающее находить и устранять ошибки в программе);

· Встроенная справочная служба.

Эти инструменты взаимодействуют между собой через обычные файлы с помощью стандартных возможностей файловой системы.

Признак классификации Типы
Набор исходных языков Одноязыковые Многоязыковые
Возможности расширения Замкнутые Открытые
Трансляция Компиляция Интерпретация

Различают системы общего назначения и языково-ориентированные системы.

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

Языково-ориентированные системы предназначены для поддержки разработки программ на каком-либо языке программирования, причем построение такой среды базируется на знаниях об этом языке.

Отличительной особенностью многоязыковых систем программирования являет то, что отдельные части (секции, модули или сегменты) программы могут быть подготовлены на различных языках и объединены во время или перед выполнением в единый модуль.

Каждый конкретный язык программирования ориентирован либо на компиляцию, либо на интерпретацию – в зависимости от того, для каких целей он создавался. Например, Pascal обычно используется для решения довольно сложных задач, в которых важна скорость работы программ. Поэтому данных язык обычно реализуется с помощью компилятора. С другой стороны, Basic создавался как язык для обучения алгоритмизации и программированию, в этом случае построчное выполнение программы делает процесс обучения более наглядным. Иногда для одного языка имеется и компилятор, и интерпретатор. В этом случае для разработки и тестирования программы можно воспользоваться интерпретатором, а затем откомпилировать отлаженную программу, чтобы повысить скорость её выполнения.

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

Популярные системы программирования: Turbo Basic, Quick Basic. Turbo Pascal, Turbo C.

Структура абстрактной многоязыковой, открытой, компилирующей СП и процесс разработки приложений:

· Ввод. Программа на исходном языке (исходный модуль) готовится с помощью текстовых редакторов и в виде текстового файла или раздела библиотеки поступает на вход компилятора.

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

Препроцессинг – необязательная фаза, состоящая в анализе исходного текста, извлечения из него директив препроцессора и их выполнения.

Директивы предпроцессора представляют собой помеченные спецсимволы (обычно %, #, &) строки, содержащие аббревиатуры, символические обозначения и т.д., конструкций, включаемых в состав исходной программы перед её обработкой компилятором.

Данные для расширения исходного текста могут быть стандартными, определяться пользователем либо содержаться в системных библиотеках ОС.

В качестве примера рассмотрим директивы, определяющие функционирование компилятора в СП Pascal.

Каждая директива компилятор заключается в фигурные скобки, и начинаются с символа «$», после которого без пробела должно быть указано имя директивы: ($I+), ($IFDEF), (@ELSE).

Различают 3 вида директив препроцессора:

· Директивы условной компиляции.

Ключевая директива включает или отключает определённые директивой возможности компилятора. Ключевые директивы могут носить глобальный или локальный характер. Глобальные директивы определяют весь процесс компиляции и должны размещаться в тексте программы до начала всех объявлений.

Локальные директивы определяют компиляцию только части кода, могут многократно включать или отключать заданные режимы компиляции и располагаться в любых местах текста программы.

Примеры ключевых директив:

Директивы параметров задают значения различных параметров, например имена файлов, размеры отводимой памяти. Ключевые директивы и директивы параметров обычно имеют установки по умолчанию.

Директивы условной компиляции позволяют в зависимости от задания тех или иных условий компилировать или исключать из программы на стали компиляции отдельные фрагменты кода. Условная компиляция даёт возможность программисту управлять компиляцией программного кода, например, использование во фрагменте кода директив:

позволит компилировать заключённый между директивами текст программы только в том случае, если включена опция Q проверки переполнения при целочисленных операциях.

Компиляция – в общем случае многоступенчатый процесс, включающий следующие фазы:

· Лексический и морфологический анализ – проверка лексического состава входного текста и перевод составных символов (операторов, скобок, идентификаторов и пр.) в некоторую промежуточную внутреннюю форму (таблицы, графы, стеки, гиперссылки), удобную для дальнейшей обработки

· Синтаксический анализ – проверка правильности конструкций, использованных программистом при подготовке текста;

· Семантический анализ – выявление несоответствий типов и структур переменных, функций и процедур;

· Генерация объектного кода – завершающая фаза трансляции.

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

Объектный модуль представляет собой текст программы на машинном языке, включающий машинные инструкции, словари, служебную информацию.

Объектный модель не работоспособен, поскольку библиотеки транслятора, реализующие функции ввода-вывода, обработки числовых и строчных переменных, а также на другие программы пользователей или средства пакетов прикладных программ.

Загрузка программы.

Загрузочный модуль после сборки либо помещается в пользовательскую библиотеку программ, либо непосредственно направляется на исполнение. Выполнение модуля состоит в загрузке его в оперативную память, настройке по месту в памяти и передаче ему управления. Образ загрузочного модуля в памяти называется абсолютным модулем, поскольку все команды ЭВМ здесь приобретают окончательную форму и получают абсолютные адреса в памяти. Формирование абсолютного модуля может осуществляться как программно путем обработки командных кодов модуля программой-загрузчиком, так и аппаратно путем применения индексирования и базирования команд загрузочного модуля и приведения указанных в них относительных адресов к абсолютной форме.
Современные системы программирования позволяет удобно переходить от одного этапа к другому. Это осуществляется в рамках так называемой интегрированной среды программирования, которая содержит в себе текстовой редактор, компилятор, компоновщик, встроенный отладчик и в зависимости от системы ее версии предоставляет программисту дополнительные удобства для написания и отладки программ.

РАЗРАБОТКА И РАЗВИТИЕ ПО.

Работа по решению прикладной задачи на компьютере происходит через следующие этапы:

1. постановка задачи;

2. математическая формализация;

4. составление программы на языке программирования;

5. отладка и тестирование программы;

6. анализ полученных результатов.

Технологическая цепочка решения задачи на ЭВМ предусматривает возможность возвратов на предыдущие этапы после анализа полученных результатов. Часто в эту цепочку включают ещё один пункт: составление сценария интерфейса (т.е. взаимодействие между пользователем и компьютером во время исполнения программы).

Постановка задачи:

1. формулировку условия задачи;

2. определение конечных целей решения задачи;

3. описание исходных данных (их типов, диапазонов возможных значений, структуры и т.п.);

4. определение формы выдачи результатов.

На этом этапе необходимо чётко определить, что именно известно и что требуется получить в результате.

Построение алгоритма.

Этап построения алгоритма предполагает формирование строгой и чёткой системы правил, определяющий последовательность действий, которая за конечное число шагов должна привести к результату. В этот этап входит:

Отладка и тестирование.

Отладка программы предполагает следующие действия:

Под отладкой программы понимается процесс испытания работы программы и исправление обнаруженных при этом ошибок. Обнаружить ошибки, связанные с нарушением правил записи программы на ЯП (синтаксические и семантические ошибки). Пользователь получает сообщение об ошибке, исправляет её и снова повторяет попытку выполнить программу.

Проверка на компьютере правильности алгоритма производится с помощью тестов. Тестом, например, можно назвать конкретный вариант значений исходных данных, для которого известен ожидаемый результат. Например, для программы решения системы линейных уравнений необходимо построить тесты, позволяющие проверить работоспособность как для варианта, когда определитель матрицы равен нулю, так и для варианта, когда решение системы существует и единственно.

Частотный принцип.

Основан на выделении в алгоритмах и в обрабатываемых структурах групп действий и данных по частоте использования. Для действий, которые часто встречаются при разработке ПО, обеспечиваются условия их наиболее быстрого выполнения. К данным, к которым происходит частое обращение, обеспечивается наиболее быстрый доступ. «Частые» операции стараются делать более короткими.

Принцип модульности.

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

Способы обособления составных частей ПО в отдельные модули могут быть существенно различными. Чаще всего разделение происходит по функциональному признаку. В значительной степени разделение системы на модули определяется используемым методом проектирования ПО.

Принцип генерируемости.

Основное положение этого принципа определяет такой способ исходного представления ПО, который бы позволял осуществлять настройку на конкретную конфигурацию ТС, круг решаемых проблем, условия работы пользователя.

Принцип «умолчания».

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

Общие системные принципы.

При создании и развитии ПО рекомендуется применять:

Типы пользователей.

Можно выделить три квалификационные категории пользователей, которые занимаются разработкой и использованием ПО:

Способность к обучению.

Человек обучается постепенно. Степень (образованности) ЭВМ определяется её ПО. Желательно, чтобы содержание информации, получаемой на запросе пользователя, могло изменяться по требованию пользователя.

Обращение с информацией.

Ёмкость мозга человека для сохранения детализированной информации невелика, но обладает интуитивной неформальной возможностью её организации. Эффективность вторичного обращения к памяти зависит от времени. В ЭВМ ёмкость памяти большая, организация – формальное и детализированное, вторичное обращение не зависит от времени. Поэтому целесообразно накапливать и организовывать информацию автоматическим путём и осуществлять её быстрый вызов по удобным для человека критериям.

Оценка информации.

Человек умеет хорошо разделять значимую и несущественную информацию, а ЭВМ таким свойством не обладает, поэтому должна существовать возможность макро просмотра информации большого объёма, что позволяет человеку выбрать интересующую его часть, не изучая всю накопленную информацию.

Отношение к ошибкам.

Человек часто допускает существенные ошибки, исправляя их интуитивно. При этом метод обнаружения ошибок чаще всего такой же интуитивный. ЭВМ наоборот не проявляет никакой терпимости к ошибкам и метод обнаружения ошибок строго систематичен. Однако, в области формальных ошибок возможности ЭВМ значительно больше, чем при обнаружении неформальных. Поэтому нужно обеспечить возможность пользователю вводить в ЭВМ исходную информацию в свободной форме. ЭВМ выполняет контроль и преобразование информации к стандартному виду, удобному в процедурах обработки и формального устранения ошибок. Затем желательно обратное преобразование этой информации для показа пользователю в наглядной, например, в графической форме для обнаружения ошибок.

Терпение.

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

Самочувствие.

ЭВМ должна беречь самочувствие пользователя, его чувство собственного достоинства и показывать ему, что именно машина его обслуживает, а не наоборот. Вопросы, ответы и замечания должны соответствовать между подчинённым и его руководителем, определяющим ход процесса проектирования.

Эмоциональность.

Это чувство свойственно человеку и чуждо ЭВМ. ПО должно возбуждать у пользователя положительные эмоции и не допускать отрицательных

Языки и среды программирования.

АЛГОРИТМЫ.

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

Способы записи алгоритмов:

Базовые структуры алгоритмов:

Источник

Лекция 1.1 Язык программирования и среда разработки

Основы объектного программирования на С#

Часть 1
Ядро языка

Цели курса

Основной целью этого курса является изучение основ объектного стиля разработки программных проектов. Для программиста, владеющего этими основами, не столь важно, на каком конкретном языке программирования или в какой среде ему необходимо разработать тот или иной программный проект – на любом языке он будет создавать программный продукт требуемого качества. Тем не менее, у каждого программиста есть свои предпочтения, свой любимый язык и среда разработки.

Язык C#

Язык C# является наиболее известной новинкой в области создания языков программирования. По сути это язык программирования, созданный уже в 21-м веке. Явившись на свет в недрах Microsoft, он с первых своих шагов получил мощную поддержку. Язык признан международным сообществом. В июне 2006 года Европейской ассоциацией по стандартизации принята уже четвертая версия стандарта этого языка: Standard ECMA-334 C# Language Specifications, 4-th edition –

Международной ассоциацией по стандартизации эта версия языка принята как стандарт ISO/IEC – 23270. Заметим, что первая версия стандарта языка принята еще в 2001 году. Компиляторы Microsoft строятся в соответствии с международными стандартами языка.

Язык C# является молодым языком и продолжает интенсивно развиваться. Каждая новая версия языка включает принципиально новые свойства. Не исключением явилась и версия 3.0, рассматриваемая в данном учебном курсе.

Руководителем группы, создающей язык C#, является сотрудник Microsoft Андреас Хейлсберг. Он стал известным в мире программистов задолго до того, как пришел в Microsoft. Хейлсберг входил в число ведущих разработчиков одной из самых популярных сред разработки – Delphi. В Microsoft он участвовал в создании версии языка Java – J++, так что опыта в написании языков и сред программирования ему не занимать. Как отмечал сам Андреас Хейлсберг, C# создавался как язык компонентного программирования, и в этом одно из главных достоинств языка, направленное на возможность повторного использования созданных компонентов. Создаваемые компилятором компоненты являются само документируемыми, помимо кода содержат метаинформацию, описывающую компоненты, и поэтому могут выполняться на различных платформах.

Отметим следующие важные факторы:

В каком направлении развивается язык C#? Назовем новинки, появившиеся в версии 3.0:

Эти и другие новинки будут подробно рассмотрены в соответствующих разделах курса.

Будущее С#

Следующая версия языка С# 4.0 должна появиться параллельно с выходом новой версии Visual Studio 2010. Продолжается работа над версией C# 5.0. Можно отметить три основные тенденции в развитии языка – декларативность, динамичность и параллельность. Разработчики языка пытаются придать языку C# свойства, расширяющие традиционные возможности процедурных языков. Явно заметен тренд к функциональным языкам с их декларативным стилем. Такие свойства появились уже в C# 3.0, в следующих версиях они только расширяются.

В новой версии Visual Studio 2010 должны появиться новые динамические языки программирования – «железный змей» — Iron Python и Iron Ruby. Эти языки проще устроены, во многом из-за того, что не являются строго типизированными и потому не позволяют проводить контроль типов еще на этапе компиляции. В C# 4.0 введена возможность задания динамических переменных, аналогично тому, как это делается в динамических языках.

Параллельные вычисления в ближайшие 5-10 лет станут реальностью повседневной работы программиста. В этом направлении развивается техника. Языки программирования должны поддерживать эту тенденцию.

Компилятор как сервис, программирование на лету, — такие возможности должны появиться в C# 5.0. Можно не сомневаться, что C# программистам в ближайшие годы скучать не придется.

Visual Studio 2008

Рассмотрим основные особенности среды разработки Visual Studio.

Открытость

Таких расширений среды Visual Studio сделано уже достаточно много, практически они существуют для всех известных языков – Fortran и Cobol, RPG и Component Pascal, Eiffel, Oberon и Smalltalk.

Новостью является то, что Microsoft не включила в Visual Studio 2008 поддержку языка Java. Допустимые в предыдущих версиях проекты на языке J++ в Visual Studio 2008 в настоящее время создавать нельзя, ранее созданные проекты в студии не открываются.

Библиотека классов FCL – статический компонент каркаса

Понятие каркаса приложений – Framework Applications появилось достаточно давно, оно широко использовалось еще в четвертой версии Visual Studio. Библиотека классов MFC (Microsoft Foundation Classes) играла роль каркаса приложений Visual C++.

Несмотря на то, что каркас был представлен только статическим компонентом, уже тогда была очевидна его роль в построении приложений. Уже в то время важнейшее значение в библиотеке классов MFC имели классы, задающие архитектуру строящихся приложений. Когда разработчик выбирал один из возможных типов приложения, например архитектуру Document-View, то в его приложение автоматически встраивались класс Document, задающий структуру документа, и класс View, задающий его визуальное представление. Класс Form и классы, задающие элементы управления, обеспечивали единый интерфейс приложений. Выбирая тип приложения, разработчик изначально получал нужную ему функциональность, поддерживаемую классами каркаса. Библиотека классов поддерживала и традиционные для программистов классы, задающие расширенную систему типов данных, в частности, динамические типы данных – списки, деревья, коллекции, шаблоны.

За прошедшие годы роль каркаса в построении приложений существенно возросла, — прежде всего, за счет появления его динамического компонента, о котором чуть позже поговорим подробнее. Что же касается статического компонента – библиотеки классов, то здесь появился ряд важных нововведений.

Единство каркаса

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

Встроенные примитивные типы

Важной частью библиотеки FCL стали классы, задающие примитивные типы, те типы, которые считаются встроенными в язык программирования. Типы каркаса покрывают основное множество встроенных типов, встречающихся в языках программирования. Типы языка программирования проецируются на соответствующие типы каркаса. Тип, называемый в языке Visual Basic – Integer, а в языках С++ и C# — int, проецируется на один и тот же тип каркаса System.Int32. В языке программирования, наряду с «родными» для языка названиями типов, разрешается пользоваться именами типов, принятыми в каркасе. Поэтому, по сути, все языки среды разработки могут пользоваться единой системой встроенных типов, что, конечно, способствует облегчению взаимодействия компонентов, написанных на разных языках.

Структурные типы

Частью библиотеки стали не только простые встроенные типы, но и структурные типы, задающие организацию данных – строки, массивы, динамические типы данных = стеки, очереди, списки, деревья. Это также способствует унификации и реальному сближению языков программирования.

Архитектура приложений

Существенно расширился набор возможных архитектурных типов построения приложений. Помимо традиционных Windows- и консольных приложений, появилась возможность построения Web-приложений. Большое внимание уделяется возможности создания повторно используемых компонентов – разрешается строить библиотеки классов, библиотеки элементов управления и библиотеки Web-элементов управления. Популярным архитектурным типом являются Web-службы, ставшие сегодня благодаря открытому стандарту одним из основных видов повторно используемых компонентов.

Модульность

Число классов библиотеки FCL велико (несколько тысяч). Поэтому понадобился способ их структуризации. Логически классы с близкой функциональностью объединяются в группы, называемые пространством имен (Namespace). Основным пространством имен библиотеки FCL является пространство System, содержащее как классы, так и другие вложенные пространства имен. Так, уже упоминавшийся примитивный тип Int32 непосредственно вложен в пространство имен System и его полное имя, включающее имя пространства – System.Int32.

В пространство System вложен целый ряд других пространств имен. Например, в пространстве System.Collections находятся классы и интерфейсы, поддерживающие работу с коллекциями объектов – списками, очередями, словарями. В пространство System.Collections, в свою очередь, вложено пространство имен Specialized, содержащие классы со специализацией, например, коллекции, элементами которых являются только строки. Пространство System.Windows.Forms содержит классы, используемые при создании Windows-приложений. Класс Form из этого пространства задает форму – окно, заполняемое элементами управления, графикой, обеспечивающее интерактивное взаимодействие с пользователем.

По ходу курса мы будем знакомиться со многими классами библиотеки FCL.

Общеязыковая исполнительная среда CLR – динамический компонент каркаса

Двухэтапная компиляция. Управляемый модуль и управляемый код

Заметьте, PE-файл, имеющий уточнение exe, хотя и является exe-файлом, но это не обычный исполняемый Windows файл. При его запуске он распознается как PE-файл и передается CLR для обработки. Исполнительная среда начинает работать с кодом, в котором специфика исходного языка программирования исчезла. Код на IL начинает выполняться под управлением CLR (по этой причине код называется управляемым). Исполнительную среду следует рассматривать как виртуальную IL-машину. Эта машина транслирует «на лету» требуемые для исполнения участки кода в команды реального процессора, который в действительности и выполняет код.

Виртуальная машина

Компилятор JIT, входящий в состав CLR, компилирует IL код с учетом особенностей текущей платформы. Благодаря этому создаются высокопроизводительные приложения. Следует отметить, что CLR, работая с IL кодом, выполняет достаточно эффективную оптимизацию и, что не менее важно, защиту кода. Зачастую нецелесообразно выполнять оптимизацию на уровне создания IL кода, она иногда может не улучшить, а ухудшить ситуацию, не давая CLR провести оптимизацию на нижнем уровне, где можно учесть особенности процессора.

Дизассемблер и ассемблер

Для проекта, построенного на C#, иногда полезно провести анализ построенного PE-файла, его IL кода и связанных с ним метаданных. В состав Framework SDK входит дизассемблер – ildasm, выполняющий дизассемблирование PE-файла и показывающий в наглядной форме метаданные и IL код с комментариями. Мы иногда будем пользоваться результатами дизассемблирования. У меня на компьютере кнопка, вызывающая дизассемблер, находится на рабочем столе. Вот путь к папке, в которой обычно находится дизассемблер:

Профессионалы, предпочитающие работать на низком уровне, могут программировать на языке ассемблера IL. В этом случае в их распоряжении будет вся мощь библиотеки FCL и все возможности CLR. У меня на компьютере путь к папке, где находится ассемблер, следующий:

В этой книге к ассемблеру мы обращаться не будем, упоминаю о нем для полноты картины.

Метаданные

Переносимый исполняемый PE-файл является само документируемым файлом и, как уже говорилось, содержит код и метаданные, описывающие код. Файл начинается с манифеста и включает в себя описание всех классов, хранимых в PE-файле, их свойств, методов, всех аргументов этих методов – всю необходимую CLR информацию. Поэтому помимо PE-файла не требуется никаких дополнительных файлов, записей в реестр, вся нужная информация извлекается из самого файла. Введение метаданных не только важная техническая часть CLR, но это также часть новой идеологии разработки программных продуктов. Мы увидим, что и на уровне языка C# само документированию уделяется большое внимание.

Мы увидим также, что при проектировании класса программист может создавать его атрибуты, добавляемые к метаданным PE-файла. Клиенты класса могут, используя классы из пространства имен Reflection, получать эту дополнительную информацию и на ее основании принимать соответствующие решения.

Сборщик мусора – Garbage Collector и управление памятью

Еще одной важной особенностью построения CLR является то, что исполнительная среда берет на себя часть функций, традиционно входящих в ведение разработчиков трансляторов, и облегчает тем самым их работу. Один из таких наиболее значимых компонентов CLR — сборщик мусора (Garbage Collector). Под сборкой мусора понимается освобождение памяти, занятой объектами, которые стали бесполезными и не используются в дальнейшей работе приложения. В ряде языков программирования (классическим примером является язык C/C++) память освобождает сам программист, в явной форме отдавая команды, как на создание, так и на удаление объекта. В этом есть своя логика – я тебя породил, я тебя и убью. Однако можно и нужно освободить человека от этой работы. Неизбежные ошибки программиста при работе с памятью тяжелы по последствиям, и их крайне тяжело обнаружить. Как правило, объект удаляется в одном модуле, а необходимость в нем обнаруживается в другом далеком модуле. Обоснование того, что программист не должен заниматься удалением объектов, а сборка мусора должна стать частью исполнительной среды, дано достаточно давно. Наиболее полно оно обосновано в работах Бертрана Мейера и в его книге «Object-Oriented Construction Software», первое издание которой появилось еще в 1988 году.

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

Но, как же, спросите вы, быть с языком C++ и другими языками, где есть нетипизированные указатели, адресная арифметика, возможности удаления объектов программистом? Ответ следующий – CLR позволяет работать как с управляемыми, так и с неуправляемыми данными. Однако использование неуправляемых данных регламентируется и не поощряется. Так, в C# модуль, использующий неуправляемые данные (указатели, адресную арифметику), должен быть помечен как небезопасный (unsafe), и эти данные должны быть четко зафиксированы. Об этом мы еще будем говорить при рассмотрении языка C# в последующих лекциях. Исполнительная среда, не ограничивая возможности языка и программистов, вводит определенную дисциплину в применении потенциально опасных средств языков программирования.

Исключительные ситуации

Что происходит, когда при вызове некоторой функции (процедуры) обнаруживается, что она не может нормальным образом выполнить свою работу? Возможны разные варианты обработки такой ситуации. Функция может возвращать код ошибки или специальное значение типа HResult, может выбрасывать исключение, тип которого характеризует возникшую ошибку. В CLR принято во всех таких ситуациях выбрасывать исключение. Косвенно это влияет и на язык программирования. Выбрасывание исключений наилучшим образом согласуется с исполнительной средой. В языке C# выбрасывание исключений, их дальнейший перехват и обработка – основной рекомендуемый способ обработки исключительных ситуаций.

События

У CLR есть свое видение того, что представляет собой тип. Есть формальное описание общей системы типов CTS – Common Type System. В соответствии с этим описанием, каждый тип, помимо полей, методов и свойств, может содержать и события. При возникновении событий в процессе работы с тем или иным объектом данного типа посылаются сообщения, которые могут получать другие объекты. Механизм обмена сообщениями основан на делегатах – функциональном типе. Надо ли говорить, что в язык C# встроен механизм событий, полностью согласованный с возможностями CLR. Мы подробно изучим все эти механизмы, рассматривая их на уровне языка.

Исполнительная среда CLR обладает мощными динамическими механизмами – сборки мусора, динамического связывания, обработки исключительных ситуаций и событий. Все эти механизмы и их реализация в CLR созданы на основании практики существующих языков программирования. Но уже созданная исполнительная среда в свою очередь влияет на языки, ориентированные на использование CLR. Поскольку язык C# создавался одновременно с созданием CLR, то, естественно, он стал языком, наиболее согласованным с исполнительной средой, и средства языка напрямую отображаются в средства исполнительной среды.

Общие спецификации и совместимые модули

LINQ и деревья выражений

Windows Presentation Foundation

В Visual Studio 2008 появились новые типы проектов, основанные на возможностях предоставляемых технологией WPF (Windows Presentation Foundation). Эта технология позволяет строить новое поколение систем презентации – с новыми графическими возможностями, связыванием данных и прочими элементами, придающими приложению принципиально новые свойства. Предполагается, что этот тип приложений постепенно будет вытеснять традиционные Windows приложения, основанные на понятии окна.

Windows Communication Foundation (WCF) и Windows Workflow Foundation (WF)

Технологии WCF и WF позволяют строить специализированные приложения и службы (Services), позволяющие приложениям обмениваться данными, используя асинхронный ввод-вывод.

Другие новинки

Управляемый и неуправляемый код

На рис. 1_1 показана схема функционирования компьютера, позволяющего выполнять как сборки – управляемый код, так и обычные exe-файлы – неуправляемый код.

Рис. 1_1 Управляемый и неуправляемый код

Заметьте, два мира программ, выполняемые по-разному, могут взаимодействовать друг с другом – из управляемого кода возможен вызов программ с неуправляемым кодом и наоборот. В проектах, написанных на C#, можно управлять офисными приложениями – документами Word и Excel. Офисные документы – это COM-объекты, принадлежащие миру неуправляемого кода, а проекты C# — это сборки – жители страны с управляемым кодом.

Проекты C# в Visual Studio 2008

При запуске Visual Studio 2008, которая, надеюсь, уже установлена на Вашем компьютере, открывается стартовая страница. В окне «Recent Projects» стартовой страницы есть две скромные, непрезентабельного вида две ссылки – «Open: Project…» и «Create Project…».

Они задают две основные функции, которые может выполнять разработчик в Visual Studio 2008, – он может открывать существующие проекты и работать с ними, или создать и работать с новым проектом. В большинстве случаев после открытия стартовой страницы щелчком по одной из ссылок мы переходим к созданию или открытию проекта. Вид стартовой страницы показан на рис. 1_2.

Рис. 1_2 Вид стартовой страницы

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

Для компьютера, подключенного к интернет, стартовая страница автоматически связывается с сайтом, содержащим текущую информацию по C# и Visual Studio 2008, — по умолчанию показываются новости с сайта msdn. Выбрав соответствующий пункт из раздела Getting Started (Давайте Начнем), можно получить информацию из центра разработчиков C#, можно подключиться к одному из трех форумов по языку C#, можно получить нужную справку в режиме «on line».

На стартовой странице, помимо вкладки «StartPage», расположена вкладка «Главная страница MSDN», позволяющая перейти к соответствующему сайту. На рис. 1_3 показана страница, открытая при выборе этой вкладки.

Рис. 1_3 Вид главной страницы MSDN

Коль скоро речь зашла о получении текущей информации и справок по языку C#, приведу несколько полезных ресурсов:

http://forums.msdn.microsoft.com/en-us/forums/ — англоязычный сайт предоставляет доступ к различным форумам, в том числе форумам по языку С#.

http://csharpfriends.com/ — англоязычный сайт, где можно найти нужную информацию, задать вопросы и получить ответы от сообщества разработчиков.

Создание проекта

Выбрав на стартовой странице ссылку «Создать проект», переходим на страницу создания нового проекта. На рис. 1_4 показан внешний вид этой страницы.

Рис. 1_4 Окно создания нового проекта

Посмотрите, какой широкий спектр возможностей предлагает Visual Studio 2008 своим разработчикам.

В окне категорий типов проекта — «Project Types» можно выбрать категорию, определяющую набор шаблонов, задающих типы проектов данной категории. Первые три категории, показанные на рисунке, задают язык программирования, на котором будут создаваться проекты. Эти категории позволяют создавать проекты на трех разных языках, включенных Microsoft в состав студии. Уже говорилось, что среда является открытой и дополнительный состав языков определяется предпочтениями разработчика. При включении нового языка в состав Visual Studio 2008 число категорий, задающих язык, будет увеличиваться.

Еще одна категория «Other Project Types» определяет шаблоны типов проектов, не связанных с языком программирования. Сюда входят проекты, предназначенные для развертывания приложений, проекты для работы с реляционными базами данных и языком запросов SQL, проекты построения Add-in, расширяющие возможности других приложений, например приложений Office.

Последняя категория «Test Projects»включает шаблон проекта, задающего тестовый документ.

Каждая категория включает подкатегории со своими шаблонами типов проектов. Суммарное число типов проектов, которые разработчик может построить в рамках Visual Studio 2008, достаточно велико. Я не думаю, что есть разработчики, которые используют в своей работе все типы проектов. И в этой книге, в этом курсе будем рассматривать только часть возможных типов проектов.

Категория проектов на языке C# включает в настоящее время 9 подкатегорий. Наиболее часто используемыми являются первые две категории — Windows и Web. Первая из них позволяет строить Windows-проекты, предназначенные для работы на локальном компьютере. Вторая подкатегория позволяет строить Web-приложения, работающие в сети интернет или интранет. Этим типам проектов, по крайней мере части из них будет уделено основное внимание в нашем курсе.

Рассмотрим чуть более подробно категорию Windows-проектов. Она включает на момент написания этого текста 10 типов проектов:

Определение основных понятий

Эта глава носит обзорный характер. В ней введено много новых понятий. Полезно дать определения введенных понятий, которые будут использоваться по ходу всего курса.

Класс (Class)

Класс – это центральное понятие объектно-ориентированного программирования и языка C#. Разработчик проектов на C# использует стандартные классы из библиотеки FCL и создает собственные классы. У класса две различные роли:

Класс – это модуль – архитектурная единица построения проекта по модульному принципу. Справиться со сложностью большого проекта можно только путем деления его на модули, — сравнительно небольшие единицы, допускающие независимую разработку и последующее объединение в большую систему.

Класс – это тип данных. Тип данных – это семантическая единица, описывающая свойства и поведение множества объектов, называемых экземплярами класса. Синтаксически класс представляет описание данных, называемых полями класса, описание методов класса и описание событий класса. Для класса, рассматриваемого как тип данных, поля определяют состояние объектов, методы – поведение объектов. События – это некоторые специальные состояния, в которых может находиться объект, и которые могут обрабатываться внешними по отношению к классу обработчиками события. Так, например, объект класса Person может иметь событие «День рождения» и каждый из обработчиков этого события может принести объекту свои поздравления по этому случаю.

Как правило, класс C# играет обе роли. Но язык C# позволяет определять классы, играющие только роль модуля. Это так называемые статические классы, для которых невозможно создавать объекты. В ходе выполнения программной системы создается единственный экземпляр такого класса, обеспечивающий доступ к полям и методам этого модуля.

Хороший стиль программирования требует, чтобы каждый класс сохранялся в отдельном файле, имя которого совпадало бы с именем класса. Это требование стиля, которое на практике может и не выдерживаться. В наших примерах будем стараться выдерживать этот стиль.

Объект (Object)

Определив класс, разработчик получает возможность динамически создавать объекты класса.
Для программистов, начинающих работать в объектном стиле, типичной ошибкой является путаница понятий объекта и класса. Нужно с самого начала уяснить разницу. Класс, создаваемый разработчиком, представляет статическое описание множества объектов. Объект – это динамическое понятие, он создается в ходе выполнения программной системы, реально существует в памяти компьютера и обычно исчезает по завершении выполнения проекта. Программист может создать программную систему, включающую два — три класса, но в ходе работы такой системы могут динамически появляться сотни объектов, взаимодействующих друг с другом достаточно сложным образом.

Заметьте, путаница понятий класса и объекта характерна и для опытных разработчиков. Показателен тот факт, что центральный класс в библиотеке FCL, являющийся прародителем всех классов как библиотечных, так и создаваемых разработчиком проектов C#, назван именем Object.

Пространство имен (Namespace)

Пространство имен – это оболочка, содержащая множество классов, объединенных, как правило, общей тематикой или группой разработчиков. Собственные имена классов внутри пространства имен должны быть уникальны. В разных пространствах могут существовать классы с одинаковыми именами. Полное или уточненное имя класса состоит из уникального имени пространства имен и собственного имени класса. В пространстве имен могут находиться как классы, так и пространства имен.

Пространства имен позволяют задать древесную структуру на множестве классов большого проекта. Они облегчают независимую разработку проекта большим коллективом разработчиков, каждая группа которого работает в своем пространстве имен.

Пространства имен придают структуру библиотеке FCL, содержащей большое число различных пространств имен, объединяющих классы определенной тематики. Центральным пространством имен библиотеки FCL является пространство System, содержащее другие пространства и классы, имеющие широкое употребление в различных проектах.

Проект (Project)

Проект – это единица компиляции. Результатом компиляции проекта является сборка. Каждый проект содержит одно или несколько пространств имен. Как уже говорилось, на начальном этапе создания проекта по заданному типу проекта автоматически строится каркас проекта, состоящий из классов, являющихся наследниками классов, входящих в состав библиотеки FCL. Так, если разработчик указывает, что он хочет построить проект типа «Windows Forms Application», то в состав каркаса проекта по умолчанию войдет класс Form1 – наследник библиотечного класса Form. Разработчик проекта населит созданную форму элементами управления – объектами соответствующих классов, тем самым расширив возможности класса, построенного по умолчанию.

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

Сборка (Assembly)

Сборка – результат компиляции проекта. Сборка представляет собой коллекцию из одного или нескольких файлов, помеченных номером версии. Каждая сборка разворачивается на компьютере как единое целое. Программист работает с проектами, CLR работает со сборками. Сборка позволяет решать вопросы безопасности, так как содержит описание требуемых ей ресурсов и права доступа к элементам сборки. Каждая сборка содержит манифест, содержащий полное описание сборки, ее элементов, требуемые ресурсы, ссылки на другие сборки, исполняемые файлы. Благодаря этому описанию CLR не требуется никакой дополнительной информации для развертывания сборки, трансляции промежуточного кода и его выполнения. Манифест идентифицирует сборку, специфицирует файлы, требуемые для реализации сборки, специфицирует типы и ресурсы, составляющие сборку, задает зависимости, необходимые в период компиляции для связи с другими сборками, специфицирует множество разрешений, необходимых, чтобы сборка могла выполняться на данном компьютере.

Решение (Solution)

Каждый проект, создаваемый в Visual Studio 2008, помещается в некоторую оболочку, называемую Решением – Solution. Решение может содержать несколько проектов, как правило, связанных общей темой. Например, все проекты, рассматриваемые в одной главе книги, я мог бы поместить в одно Решение. В наших примерах зачастую Решение будет содержать три проекта – DLL с классами, определяющими содержательную сторону приложения, и два интерфейсных проекта – консольный и Windows.

Когда создается новый проект, то он может быть помещен в уже существующее Решение или может быть создано новое Решение, содержащее проект.

Решения позволяют придать структуру множеству проектов, что особенно полезно, когда проектов много.

Пример

Один из принципов, которых я придерживаюсь при написании книг по программированию, состоит в том, что в таких книгах программный код должен составлять существенную часть текста. Этот код следует читать и изучать не менее внимательно, чем обычный текст. Зачастую он говорит больше чем рассуждения автора. Поэтому и данная глава заканчивается примером, иллюстрирующим основные понятия, введенные в главе. Я отказался от традиции начинать с классического приложения «Здравствуй, мир!». Для первого рассмотрения наш пример будет достаточно сложным, — мы построим Решение, содержащее три проекта – проект DLL, консольный проект и Windows-проект.

Постановка задачи

Начну с описания содержательной постановки задачи. Вначале некоторая преамбула. В системе типов языка C# есть несколько типов, задающих различные подмножества арифметического типа данных – int, double и другие. Для значения x любого из этих типов хорошо бы уметь вычислять математические функции – sin(x), ln(x) и другие. Встраивать вычисление этих функций в каждый из классов, задающих соответствующий арифметический подтип, кажется неразумным. Поэтому в библиотеку FCL включен класс Math, методы которого позволяют вычислять по заданному аргументу нужную математическую функцию. Класс Math является примером статического класса, играющего единственную роль – роль модуля. У этого класса нет собственных данных, если не считать двух математических констант – e и π, а его методы являются сервисами, которые он предоставляет другим классам.

Построим аналог класса Math и поместим этот класс в DLL, что позволит повторно использовать его, присоединяя при необходимости к различным проектам. В нашем примере не будем моделировать все сервисы класса Math. Рассмотрим вначале вычисление функции sin(x). Эту функцию, как и другие математические функции, можно вычислить, используя разложение в ряд Тэйлора:

Детали вычислений, использующих формулу (1), отложим на момент реализации. А пока продолжим уточнять цель нашего примера. Итак, мы хотим построить DLL – динамическую подключаемую библиотеку, содержащую аналог класса Math из библиотеки FCL. Затем мы хотим построить консольный проект, позволяющий провести тестирование корректности вычислений функций построенного нами класса. Затем мы построим Windows-проект, интерфейс которого позволит провести некоторые интересные исследования. Все три проекта будут находиться в одном Решении (Solution).

Создание DLL — проекта типа «Class Library»

Запустим Visual Studio 2008, со стартовой страницы перейдем к созданию проекта и в качестве типа проекта укажем тип «Class Library». В открывшемся окне создания DLL, показанном на рис. 1_5, все поля заполнены значениями по умолчанию. Как правило, их следует переопределить, задавая собственную информацию.

Рис. 1_5 Создание проекта DLL

В поле Name задается имя строящейся DLL – MathTools в нашем случае.

В поле Location указывается путь к папке, где будет храниться Решение, содержащее проект. Для Решений этой книги создана специальная папка.

В поле Solution выбран элемент «Create New Solution», создающий новое Решение. Альтернативой является элемент списка, указывающий, что проект может быть добавлен к существующему Решению.

В окне Solution Name задано имя Решения. Здесь выбрано имя Ch1, указывающее на то, что все проекты первой главы вложены в одно Решение.

Рис. 1_6 Среда Visual Studio 2008 с начальным проектом DLL

Среду разработки можно настраивать, открывая или закрывая те или иные окна, перемещая и располагая их по своему вкусу. Это делается стандартным способом, и я не буду на этом останавливаться.

В окне проектов Solution Explorer показано Решение с именем «Ch1», содержащее проект DLL с именем «MathTools». В папке «Properties» проект содержит файл с описанием сборки – ее имя и другие характеристики. В папке «References» проект содержит ссылки на основные пространства имен библиотеки FCL, которые могут понадобиться в процессе работы DLL.

Поскольку всякая DLL содержит один или несколько классов, то для одного класса, которому по умолчанию дано имя «Class1», заготовка построена. Класс этот, показанный в окне кода, пока что пуст – не содержит никаких элементов.

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

Мы рассмотрели подготовительную часть работы, которую Visual Studio 2008 выполнила для нас. Дальше предстоит потрудиться самим. С чего следует начать? С переименования! Важное правило стиля программирования говорит, что имена классов должны быть содержательными. Изменим имя «Class1» на имя «MyMath». Как следует правильно изменять имена объектов в проектах? Никак не вручную. В окне кода проекта выделите имя изменяемого объекта, затем в главном меню выберите пункт Refactor и подпункт Rename. В открывшемся окне укажите новое имя. Тогда будут показаны все места, требующие переименования объекта. В данном случае будет только одна очевидная замена, но в общем случае замен много, так что автоматическая замена всех вхождений крайне полезна.

Следующий шаг также продиктован правилом стиля – имя класса и имя файла, хранящего класс, должны совпадать. Переименование имени файла делается непосредственно в окне проектов Solution Explorer.

И следующий шаг продиктован крайне важным правилом стиля, имеющим собственное название – правило «И не вздумайте!», которое гласит — и не вздумайте написать класс без заголовочного комментария. Для добавления комментария достаточно в строке, предшествующей заголовку класса набрать три подряд идущих слеша (три косых черты). В результате перед заголовком класса появится заголовочный комментарий – тэг «summary», в который и следует добавить краткое, но содержательное описание сути класса. Тэги «summary», которыми следует сопровождать классы, открытые (public) методы и поля класса играют три важные роли. Они облегчают разработку и сопровождение проекта, делая его само документируемым. Клиенты класса при создании объектов класса получают интеллектуальную подсказку, поясняющую суть того, что можно делать с объектами. Специальный инструментарий позволяет построить документацию по проекту, включающую информацию из тегов «summary». В нашем случае комментарий к классу MyMath может быть достаточно простым – «Аналог класса Math библиотеки FCL».

Поскольку мы хотим создать аналог класса Math, то в нашем классе должны быть аналогичные методы. Начнем, как уже говорилось, с метода, позволяющего вычислить функцию sin(x). Заголовок метода сделаем такой же, как и в классе аналоге. Согласно правилу стиля «И не вздумайте» зададим заголовочный комментарий к методу. В результате в тело класса добавим следующий код:

угол в радианах — аргумент функции Sin

/// Возвращает значение функции Sin для заданного угла

public static double Sin(double x)

Осталось написать реализацию вычисления функции, заданную формулой (1). Как и во всяком реальном программировании для этого требуется знание некоторых алгоритмов. Алгоритмы вычисления конечных и бесконечных сумм относятся к элементарным алгоритмам, изучаемым в самом начале программистских курсов. Хотя этот учебник я пишу в ориентации на лиц, владеющих программированием и основами алгоритмических знаний, но я хотел бы, чтобы он был доступен и для тех, для кого C# является первым языком программирования. Поэтому прежде, чем написать программный текст, несколько слов о том, как вычислять конечные и бесконечные суммы, аналогичные формуле (1), задающей вычисление функции sin(x). Искушенные читатели могут пропустить этот текст.

Вычисление конечных и бесконечных сумм

Вычисление конечных сумм и произведений – это наиболее часто встречающийся тип элементарных задач, шаблон решения которых должен быть заучен, как 2*2. Какова бы не была сложность выражений, стоящих под знаком конечной суммы с заданным числом слагаемых, задачу всегда можно записать в виде:

и применить для ее решения следующий шаблон:

//Вычислить новое значение ak

При применении этого шаблона предполагается, что в разделе Init объявляются и должным образом инициализируются нужные переменные – S, ak, k. По завершению цикла переменная S содержит значение функции, вычисленное с заданной точностью.

Теперь мы готовы расширить определение класса, добавив код метода.

Приведем полный код проекта DLL, построенный на данный момент:

/// Аналог класса Math библиотеки FCL

public class MyMath

const double TWOPI = 2 * Math.PI;

const double EPS = 1E-9;

//Статические методы класса

/// угол в радианах — аргумент функции Sin

/// Возвращает значение функции Sin для заданного угла

public static double Sin(double x)

//Оптимизация — приведение к интервалу

while (Math.Abs(a) > EPS)

Поставленная цель достигнута, — построена DLL, содержащая класс, метод которого позволяет вычислять по заданному аргументу x функцию sin(x). Метод построен в полном соответствии с описанным алгоритмом. При его построении использованы две важные оптимизации. Во-первых, применено рекуррентное соотношение, позволяющее существенно ускорить время и точность вычисления функции – попробуйте объяснить, почему улучшаются оба эти параметра. Во-вторых, аргумент x приведен к сравнительно небольшому интервалу, что увеличивает скорость сходимости и гарантирует работоспособность метода для больших значений x. Если не делать этой оптимизации, то для больших по модулю значений метод может давать некорректные результаты, – проверьте это предположение.

Итак, все хорошо? Не совсем. Оптимизацию можно продолжить, правда, не столь уже существенную. Сейчас для вычисления значения переменной a требуется выполнить одно деление, пять умножений, два сложения, взятие результата с обратным знаком. Попробуйте самостоятельно написать новую версию метода с улучшенными показателями, не глядя на код, который я сейчас приведу. Я добавил в класс новую версию метода, сохранив для новой версии имя метода – Sin. В классе остался и старый метод, но уже с именем SinOld. Две версии, давая один и тот же результат вычислений, позволят нам в дальнейшем провести некоторые полезные исследования.

Вот код метода с дополнительной оптимизацией:

public static double Sin(double x)

//Оптимизация — приведение к интервалу

while (Math.Abs(a) > EPS)

Код метода стал элегантнее, короче, вместо пяти умножений теперь делается только два, и вместо двух сложений – одно.

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

А теперь вернемся к технической стороне дела. Построим Решение, содержащее проект, для чего в Главном меню среды выберем пункт Build | Build Solution. В результате успешной компиляции будет построен файл с уточнением dll. Поскольку построенная сборка не содержит выполняемого файла, то непосредственно запустить наш проект на выполнение не удастся. Построим консольный проект, к которому присоединим нашу DLL, и протестируем, насколько корректно работают созданные нами методы. Заодно разберемся с тем, как строится консольный проект и как к нему подсоединяется сборка, содержащая DLL.

Консольный проект

Наша цель состоит в том, чтобы построить интерфейс, обеспечивающий конечному пользователю доступ к тем сервисам, которые предоставляет построенная DLL. Начнем с построения простейшего интерфейса, позволяющего пользователю с консоли вводить исходную информацию – в нашем случае аргумент x. С исходными данными пользователь может провести вычисления, вызвав сервисы, предоставляемые DLL, а затем полученные результаты вывести на консоль – экран дисплея. Для организации подобного интерфейса и служит тип проекта – Console Application.

Чтобы создать новый проект, находясь в среде разработки, вовсе не обязательно начинать со стартовой страницы. Достаточно выбрать пункт меню File|New|Project, приводящий на страницу создания нового проекта, показанную на рис. 1_5. В этом окне, как описано ранее, зададим тип строящегося проекта, дадим ему имя – ConsoleToMathTools, укажем, что проект добавляется к существующему Решению Ch1. В результате в уже существующее Решение добавится еще один проект, что отображено на рис. 1_7

Рис. 1_7 Решение, включающее консольный проект

Как показано на рис. 1_7 в консольном проекте автоматически создается класс с именем Program, содержащий единственный статический метод – процедуру Main. Если скомпилировать этот проект и запустить его на выполнение, то начнет выполняться код этой процедуры, пока отсутствующий и который предстоит нам создать.

Начало начал – точка «большого взрыва»

Основной операцией, инициирующей вычисления в объектно-ориентированных приложениях, является вызов метода F некоторого класса, имеющий вид:

Но как появляются объекты? Как они становятся текущими? Как реализуется самый первый вызов метода, другими словами, кто и где вызывает точку входа – метод Main? С чего все начинается?

Когда Решение запускается на выполнение, то в него должна входить сборка, отмеченная как стартовый проект, содержащая класс с точкой входа – статическим методом (процедурой) Main. Некоторый объект исполнительной среды CLR и вызывает этот метод, так что первоначальный вызов метода осуществляется извне приложения. Это и есть точка «большого взрыва» – начало зарождения мира объектов и объектных вычислений. Извне создается и первый объект, задающий статический модуль с методом Main. Этот объект и становится текущим.

Дальнейший сценарий зависит от содержимого точки входа. Как правило, в процессе работы метода Main создаются один или несколько объектов других классов, они и вызывают методы и/или обработчики событий, происходящих с созданными объектами. В этих методах и обработчиках событий могут создаваться новые объекты, вызываться новые методы и новые обработчики. Так, начиная с одной точки, разворачивается целый мир объектов приложения.

Связывание с DLL

Первым делом свяжем два построенных проекта, для чего в консольный проект добавим ссылку на проект с DLL MathTools. В окне Solution Explorer подведем указатель мыши к имени консольного проекта и из контекстного меню, появляющегося при щелчке правой кнопки, выберем пункт меню «Add Reference». В открывшемся окне добавления ссылок выберем вкладку «Projects». Поскольку проект MathTools включен в Решение, то он автоматически появится в открывшемся окне. Если ссылку нужно установить на проект, не включенный в Решение, то в окне добавления ссылок нужно задать путь к проекту. Нам проще, путь указывать не нужно, достаточно щелкнуть по появившемуся в окне имени MathTools. Ссылка на DLL появится в папке «References» консольного проекта. Теперь проекты связаны и из консольного проекта доступны сервисы, предоставляемые DLL.

Организация консольного интерфейса

Задача кода, который встроим непосредственно в уже созданную процедуру Main, достаточно понятна. Необходимо объявить и создать объекты, представляющие входные данные, организовать диалог с пользователем для ввода этих данных, обратиться к сервисам DLL для получения результата и результаты вывести на консоль. Приведу вначале код консольного проекта с построенным методом Main, а затем его прокомментирую. Вот этот код:

/// Точка входа в консольный проект

/// организация интерфейса к DLL MathTools

static void Main(string[] args)

const string INVITE =

«Введите вещественное число x» +

«- аргумент функции Sin(x)»;

const string CONTINUE =

string answer = «yes»;

//Организация ввода данных

string temp = Console.ReadLine();

//Вычисления и вывод результата

//диалог с пользователем

Дадим краткие комментарии к этому коду:

Входные данные устроены просто – задается лишь одна переменная x типа double. Помните, что в языке C# все переменные являются объектами.

Вводу значения x предшествует, как и положено для хорошего стиля программирования, приглашение к вводу. Для ввода и вывода значений используются статические методы ReadLine и WriteLine класса Console, входящего в библиотеку FCL и предоставляющего свои сервисы пользователям консольных приложений. Для преобразования введенных данных, представляющих собой строки текста, к нужному типу (в нашем случае к типу double) используются статические методы класса Convert, сервисы которого позволяют проводить различные преобразования между типами данных.

Значение функции Sin(x) вычисляется тремя разными методами – методом стандартного класса Math и двумя методами класса MyMath, входящего в состав библиотеки MathTools.

Следуя правилу стиля “Имена константам» в коде метода используются именованные константы.

Применяется стандартный прием зацикливания тела метода Main, позволяющий пользователю самому решать, когда прервать выполнение метода.

На рис. 1_8 показаны результаты работы консольного проекта:

Рис. 1_8 Результаты работы консольного проекта

Анализируя эти результаты можно видеть, что все три метода на всех исследуемых аргументах дают одинаковые результаты, совпадающие с точностью до 9 цифр после запятой. Точность методов в классе MyMath обеспечивается константой EPS этого класса. Достигнутая точность вполне достаточна для большинства практических задач. Остается понять, насколько написанные нами методы проигрывают методу стандартного класса по времени. Это исследование оставим для следующего проекта – Windows проекта, обеспечивающего интерфейс, дающий пользователю больше возможностей.

Windows проект

Рис. 1_9 Решение, содержащее три проекта – Class Library, Console, Windows

При создании проекта DLL автоматически создавался в проекте один пустой класс, в консольном проекте создавался класс, содержащий метод Main с пустым кодом метода. В Windows проекте автоматически создаются два класса – класс с именем Form1 и класс с именем Program.

Первый из этих классов является наследником класса Form из библиотеки FCL и наследует все свойства и поведение (методы и события) родительского класса. Класс Form поддерживает организацию интерфейса пользователя в визуальном стиле. Форма является контейнером для размещения визуальных элементов управления – кнопок (Button), текстовых полей (TextBox), списков (ListBox) и более экзотичных элементов – таблиц (DataGridView), деревьев (TreeView) и многих других элементов. С некоторыми элементами управления мы познакомимся уже в этом примере, другие будут встречаться в соответствующих местах нашего курса.

Построение интерфейса формы

Прежде чем заняться построением интерфейса формы, переименуем класс Form1, дав ему, как положено, содержательное имя – FormResearchSinus. Заметьте, переименование объектов класса хотя и можно делать руками, но это далеко не лучший способ, чреватый ошибками. Для этих целей следует использовать возможности, предоставляемые меню Refactor | Rename. Параллельно с переименованием класса следует переименовать и файл (файлы) с описанием класса.

Займемся теперь построением интерфейса – размещением в форме элементов управления. Классическим примером интерфейса, поддерживающего сервисы стандартного класса Math, является инженерный калькулятор. В нашем классе реализована пока только одна функция – sin(x), так что можем построить пока калькулятор одной функции. Но и цели у нас другие – мы занимаемся исследованием того, насколько корректно и точно предложенные алгоритмы позволяют вычислить эту функцию.

Проведем еще одно важное исследование – оценим время, затрачиваемое на вычисление функции. Временные оценки работы проекта и его отдельных частей крайне важная часть работы разработчика проекта. Во многих случаях требуется построить временной профиль работы проекта, выявить его наиболее узкие места, на выполнение которых уходит основное время работы, что позволит целенаправленно заниматься оптимизацией проекта, направленной на уменьшение времени работы. Следует помнить, что интерактивный стиль работы современных приложений требует быстрой реакции системы на действия пользователя. Пользователь имеет право задумываться при выборе своих действий, но от системы в большинстве случаев ждет немедленного ответа. Так что поставим цель – получить время, затрачиваемое компьютером на вычисление функции как стандартным методом класса Math, так и методами класса MyMath из библиотеки MathTools.

На рис. 1_10 показан интерфейс спроектированной формы:

Рис. 1_10 Интерфейс формы класса FormResearchSinus

Для наших целей достаточен скромный интерфейс. В форму включено текстовое поле для ввода значения аргумента x, три текстовых поля предназначены для отображения результата вычислений функции sin(x) тремя различными методами. В форме есть отдельный контейнер для оценки временных характеристик. В контейнер помещены три текстовых поля, в которых будет отображаться время, затрачиваемое на вычисление функции каждым из анализируемых методов. Поскольку компьютеры быстрые, то замерить время, требуемое на однократное вычисление функции, просто невозможно. Замеряется время, затрачиваемое на многократное выполнение метода (отдельного участка кода). В контейнере размещено окно, позволяющее задать число повторов вычисления функции при измерении времени работы. Все текстовые поля снабжены метками, проясняющими смысл каждого поля. Для входных текстовых полей (аргумент функции и число повторов) заданы значения по умолчанию. В форме находится командная кнопка, щелчок по которой приводит к возникновению события Click этого объекта, а обработчик этого события запускает вычисление значений функции, получение оценок времени вычисления и вывод результатов в соответствующие текстовые поля. Каков сценарий работы пользователя? Когда при запуске проекта открывается форма, то пользователь может в соответствующих полях задать значение аргумента функции и число повторов, после чего нажать кнопку с надписью «Вычислить sin(x)». В выходных текстовых полях появятся результаты вычислений. Меняя входные данные можно наблюдать, как меняются результаты вычислений. Можно убедиться, что при всех задаваемых значениях аргумента функции значения функции, вычисленное тремя разными методами совпадают с точностью до 9 знаков после запятой, а время вычислений метода, встроенного в стандартный класс Math, примерно в два раза меньше, чем время спроектированных нами методов, что впрочем не удивительно и вполне ожидаемо. Реализация вычисления стандартных математических функций реализована на аппаратном уровне, поэтому практически невозможно написать собственный код, работающий эффективнее.

В классе MyMath для вычисления функции sin(x) построены два метода, для одного из которых проведена дополнительная оптимизация. Оценить ее эффективность не так просто, поскольку при оценке времени работы возможны погрешности, измеряемые десятками миллисекунд, что сравнимо с выигрышем, полученным в результате оптимизации.

Как оценить время работы метода

Имея в своем арсенале такой класс, не стоит большого труда измерить время, требуемое на выполнение некоторого участка кода. Достаточно иметь две переменные с именами, например, start и finish класса DateTime. Переменой start присвоить значение, возвращаемое функцией Now перед началом измеряемого участка кода, а переменной finish – в конце участка кода. Разность времен даст нам требуемую оценку длительности выполнения кода.

Некоторый недостаток этого подхода состоит в том, что рабочий код нужно дополнять операторами, нужными только для проведения исследований. Поэтому хочется иметь более удобный инструментарий, и я покажу возможный образец построения подобного инструмента. В созданной нами библиотеке MathTools будем сохранять инструменты, предназначенные для повторного использования. Добавим в эту библиотеку новый класс. Вот описание этого класса, пока пустого, но содержащего заголовочный комментарий:

/// Класс спроектирован для получения оценок времени

Источник