Дослідження особливостей проектування мережевих додатків на базі платформи dotNet

Теоретичні аспекти проектування мережевих додатків. Опис середовища розробки Visual Studio .NET. Експериментальне дослідження та опис програмної реалізації. Опис інтерфейсу користувача. Економічне обґрунтування доцільності розробки програмного продукту.

Рубрика Программирование, компьютеры и кибернетика
Вид дипломная работа
Язык украинский
Дата добавления 22.10.2012
Размер файла 2,2 M

Отправить свою хорошую работу в базу знаний просто. Используйте форму, расположенную ниже

Студенты, аспиранты, молодые ученые, использующие базу знаний в своей учебе и работе, будут вам очень благодарны.

У стеку TCP/IP маршрутизатори і кінцеві вузли приймають рішення про той, кому передавати пакет для його успішної доставки вузлу призначення, на підставі так званих таблиць маршрутизації (routing tables ).

Наступна таблиця є типовим прикладом таблиці маршрутів, що використовує IP-адреса мереж:

Адреса сети назначения

Адреса наступного маршрутизатора

Номер выходного портаРасстояние до сети призначення

56.0.0.0

198.21.17.7

120

56.0.0.0

213.34.12.4.

2130

116.0.0.0

213.34.12.4

21450

129.13.0.0

198.21.17.6

150

198.21.17.0

-

20

213. 34.12.0

-

10

У цій таблиці в стовпці "Адреса мережі призначення" вказуються адреси всіх мереж, яким даний маршрутизатор може передавати пакети. У стеку TCP/IP прийнятий так званий однокроковий підхід до оптимізації маршруту просування пакету (next-hop routing ) - кожен маршрутизатор і кінцевий вузол бере участь у виборі лише одного кроку передачі пакету. Тому в кожному рядку таблиці маршрутизації вказується не весь маршрут у вигляді послідовності IP-адресов маршрутизаторів, через які повинен пройти пакет, а лише один IP-адрес - адреса наступного маршрутизатора, якому потрібно передати пакет. Разом з пакетом наступному маршрутизатору передається відповідальність за вибір наступного кроку маршрутизації. Однокроковий підхід до маршрутизації означає розподілене рішення задачі вибору маршруту. Це знімає обмеження на максимальну кількість транзитних маршрутизаторів на дорозі пакету.

(Альтернативою однокроковому підходу є вказівка в пакеті всієї послідовності маршрутизаторів, які пакет повинен пройти на своїй дорозі . Такий підхід називається маршрутизацією від джерела - Source Routing . В цьому випадку вибір маршруту проводиться кінцевим вузлом або першим маршрутизатором на дорозі пакету, а всі останні маршрутизатори лише відпрацьовують вибраний маршрут, здійснюючи комутацію пакетів, тобто передачу їх з одного порту на іншій. Алгоритм Source Routing застосовується в мережах IP лише для відладки, коли маршрут задається в полі Резерв (IP OPTIONS ) пакету.)

У випадку, якщо в таблиці маршрутів є більш за один рядок, відповідний одній і тому ж адресі мережі призначення, то при ухваленні рішення про передачу пакету використовується той рядок, в якому вказано найменше значення в полі "Відстань до мережі призначення".

При цьому під відстанню розуміється будь-яка метрика, використовувана відповідно до заданого в мережевому пакеті класу сервісу. Це може бути кількість транзитних маршрутизаторів в даному маршруті (кількість хопов від hop - стрибок), час проходження пакету по лініях зв'язку, надійність ліній зв'язку, або інша величина, що відображає якість даного маршруту по відношенню до конкретного класу сервісу. Якщо маршрутизатор підтримує декілька класів сервісу пакетів, то таблиця маршрутів складається і застосовується окремо для кожного виду сервісу (критерію вибору маршруту).

Для відправки пакету наступному маршрутизатору потрібне знання його локальної адреси, але в стеку TCP/IP в таблицях маршрутизації прийнято використання лише IP-адресов для збереження їх універсального формату, не залежного від типа мереж, що входять в інтермережу. Для знаходження локальної адреси по відомій IP-адресу необхідно скористатися протоколом ARP .

Кінцевий вузол, як і маршрутизатор, має в своєму розпорядженні таблицю маршрутів уніфікованого формату і на підставі її даних приймає рішення, якому маршрутизатору потрібно передавати пакет для мережі N. Рішення про те, що цей пакет потрібно взагалі маршрутизувати, комп'ютер приймає у тому випадку, коли він бачить, що адреса мережі призначення пакету відрізняється від адреси його власної мережі (кожному комп'ютеру при конфігурації адміністратор привласнює його IP-адрес або декілька IP-адресов , якщо комп'ютер одночасно підключений до декількох мереж). Коли комп'ютер вибрав наступний маршрутизатор, то він переглядають кеш-таблицю адрес свого протоколу ARP і, можливо, знаходить там відповідність IP-адреса наступного маршрутизатора його MAC-адресу . Якщо ж немає, то по локальній мережі передається широкомовний ARP-запрос і локальна адреса витягується з ARP-ответа .

Після цього комп'ютер формує кадр протоколу, використовуваного на вибраному порту, наприклад, кадр Ethernet , в який поміщає МАС-адрес маршрутизатора. Маршрутизатор приймає кадр Ethernet , витягує з нього пакет IP і переглядає свою таблицю маршрутизації для знаходження наступного маршрутизатора. При цьому він виконує ті ж дії, що і кінцевий вузол.

Однокрокова маршрутизація володіє ще однією перевагою - вона дозволяє скоротити об'єм таблиць маршрутизації в кінцевих вузлах і маршрутизаторах за рахунок використання як номер мережі призначення так званого маршруту за умовчанням - default , який зазвичай займає в таблиці маршрутизації останній рядок. Якщо в таблиці маршрутизації є такий запис, то всі пакети з номерами мереж, які відсутні в таблиці маршрутизації, передаються маршрутизатору, вказаному в рядку default . Тому маршрутизатори часто зберігають в своїх таблицях обмежену інформацію про мережі інтермережі, пересилаючи пакети для останніх мереж в порт і маршрутизатор, використовувані за умовчанням. Мається на увазі, що маршрутизатор, використовуваний за умовчанням, передасть пакет на магістральну мережу, а маршрутизатори, підключені до магістралі, мають повну інформацію про склад інтермережі.

Особливо часто прийомом маршрутизації за умовчанням користуються кінцеві вузли. Хоча вони також в загальному випадку мають в своєму розпорядженні таблицю маршрутизації, її об'єм зазвичай незначний, оскільки маршрутизація для комп'ютера - не основне заняття. Головна роль в маршрутизації пакетів в концепції протоколу IP відводиться, природно, маршрутизаторам, які повинні володіти набагато повнішими таблицями маршрутизації, чим кінцеві вузли. Кінцевий вузол часто взагалі працює без таблиці маршрутизації, маючи лише зведення про IP-адресе маршрутизатора за умовчанням. За наявності одного маршрутизатора в локальній мережі цей варіант - єдино можливий для всіх кінцевих вузлів. Але навіть за наявності декількох маршрутизаторів в локальній мережі, коли проблема їх вибору стоїть перед кінцевим вузлом, завдання маршруту за умовчанням часто використовується в комп'ютерах для скорочення об'єму їх маршрутної таблиці.

Іншим способом розвантаження комп'ютера від необхідності ведення великих таблиць маршрутизації є здобуття від маршрутизатора відомостей про раціональний маршрут для якої-небудь конкретної мережі за допомогою протоколу ICMP .

Окрім маршруту default , в таблиці маршрутизації можуть зустрітися два типи спеціальних записів - запис про специфічний для вузла маршрут і запис про адреси мереж, безпосередньо підключених до портів маршрутизатора.

Специфічний для вузла маршрут містить замість номера мережі повну IP-адрес , тобто адреса, що має ненульову інформацію не лише в полі номера мережі, але і в полі номера вузла. Передбачається , що для такого кінцевого вузла маршрут повинен вибиратися не так, як для всіх останніх вузлів мережі, до якої він відноситься. У разі, коли в таблиці є різні записи про просування пакетів для всієї мережі N і її окремого вузла, що має адресу N,D , під час вступу пакету, адресованого вузлу N,D , маршрутизатор віддасть перевага запису для N,D .

Записи в таблиці маршрутизації, що відносяться до мереж, безпосередньо підключених до маршрутизатора, в полі "Відстань до мережі призначення" містять нулі .

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

Існують різні алгоритми побудови таблиць для однокрокової маршрутизації. Їх можна розділити на три класи:

· алгоритми фіксованої маршрутизації

· алгоритми простої маршрутизації

· алгоритми адаптивної маршрутизації.

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

Фіксована маршрутизація

Цей алгоритм застосовується в мережах з простий топологією зв'язків і заснований на ручному складанні таблиці маршрутизації адміністратором мережі. Алгоритм часто ефективно працює також для магістралей крупних мереж, оскільки сама магістраль може мати просту структуру з очевидними найкращими дорогами дотримання пакетів в підмережі, приєднані до магістралі.

Розрізняють одинмаршрутні таблиці, в яких для кожного адресата задана одна дорога , і багатомаршрутні таблиці, що визначають декілька альтернативних доріг для кожного адресата. При використанні багатомаршрутних таблиць має бути задане правило вибору одного з них. Частіше всього одна дорога є основною, а останні - резервними.

Проста маршрутизація

Алгоритми простий маршрутизації підрозділяються на три підкласи:

Випадкова маршрутизація - пакети передаються в будь-якому, випадковому напрямі , окрім початкового.

Лавинна маршрутизація - пакети передаються на всіх напрямках, окрім початкового (застосовується в мостах для пакетів з невідомою адресою доставки).

Маршрутизація по попередньому досвіду - таблиці маршрутів складаються на підставі даних, що містяться в пакетах, що проходять через маршрутизатор. Саме так працюють прозорі мости, збираючи зведення про адреси вузлів, що входять в сегменти мережі. Такий спосіб маршрутизації володіє таким, що повільною адаптується до змін топології мережі.

Адаптивна маршрутизація

Це основний вигляд алгоритмів маршрутизації, що застосовуються маршрутизаторами в сучасних мережах із складною топологією. Адаптивна маршрутизація заснована на тому, що маршрутизатори періодично обмінюються спеціальною топологічною інформацією про наявні в інтермережі мережі, а також про зв'язки між маршрутизаторами. Зазвичай враховується не лише топологія зв'язків, але і їх пропускна спроможність і стан.

Адаптивні протоколи дозволяють всім маршрутизаторам збирати інформацію про топологію зв'язків в мережі, оперативно відпрацьовує всі зміни конфігурації зв'язків. Ці протоколи мають розподілений характер, який виражається в тому, що в мережі відсутні які-небудь виділені маршрутизатори, які б збирали і узагальнювали топологічну інформацію: ця робота розподілена між всіма маршрутизаторами.

3. Опис середовища розробки VISUAL STUDIO .NET

3.1 Основи роботи з Visual Studio .NET

Microsoft - це інтегроване середовище розробки (Integrated Development Environment (IDE)) для створення, документування, запуску і відладки програм, написаних на мовах .NET. Це могутній інструмент професійної розробки складних додатків. Набір його функцій надзвичайно великий, розглянемо його основні елементи.

Коли ми запускаємо Visual Studio .NET, то бачимо наступне вікно:

Рис. 3.1 Головне вікно середовища розробки

Початкова сторінка (Start Page) містить наступні вкладки: Projects, Online Resources і My Profile. За умовчанням ми знаходимося на вкладці Projects, на якій розташований список недавніх проектів. Ми можемо перейти по гіперпосиланню від назви проекту і відразу продовжити роботу над ним. На цій же вкладці розташовані кнопки New Project і Open Project, по натисненню на які ми запустимо діалогові вікна створення нового або відкриття існуючого документа відповідно.

На вкладці Online Resources відображаються групи новин, заголовки і посилання ресурсів розробників. Ця опція доступна, коли комп'ютер підключений до Інтернету.

Вкладка My Profile дозволяє налаштувати інтерфейс Visual Studio .NET по своєму смаку. Якщо є досвід роботи з іншими пакетам розробки, то можна вибрати звичну розкладку клавіатури, розташування вікон в цій категорії. Тут же можна задати дію при запуску, наприклад, відкриття діалогового вікна створення проекту.

Рис. 3.2 Визначення дії при запуску програми

Панелі, що ховаються, розташовані з боків вікна, -- такі як зображені на рис. 3.1 Server Explorer або Toolbox, -- можна висунути, просто клацнувши на них. Ми можемо закріпити їх на екрані, натиснувши на значок, або зовсім прибрати з екрану, а потім знову відобразити, використовуючи відповідний пункт меню View (або еквівалентне поєднання клавіш).

Головне вікно Visual Studio.NET, подібно до інших додатків Windows, містить рядок меню, що включає наступні категорії (коли ми знаходимося на Start Page, частина категорій не видно - вона з'явиться пізніше, коли буде створений проект).

У цих категоріях розташовані наступні команди:

File -- відкриття, створення, додавання, закривання, друк і інш.

Edit -- стандартні команди правки: копіювання, вставка, вирізування і інш.

View -- команди для утаєння і відображення всіх вікон і панелей інструментів.

Project -- команди для роботи з проектом: додавання елементів, форм, посилань і інш.

Build -- команди компіляції програми.

Debug -- команди для відладки програми.

Data -- команди для роботи з даними.

Format -- команди форматування елементів, що розташовуються (вирівнювання, інтервал і інш.).

Tools -- команди додаткових інструментів і настройки Visual Studio .NET.

Window -- управління розташуванням вікон.

Help -- довідка.

3.2 Форми

Всякий раз, коли ми працюємо з якою-небудь програмою, ми бачимо на екрані прямокутне вікно. У цьому вікні і розташовується вся інформація, яка нам потрібна. Форми можуть мати стандартний вигляд, такий, наприклад, як у програми Microsoft Word. Отже, форма -- це екранний об'єкт, що забезпечує функціональність програми.

Запускаємо Visual Studio .NET, вибираємо File/New/Project -- з'являється діалогове вікно (Ctrl+Shift+N приводить до того ж результату), в якому вибираємо Visual C# Project і Windows Application.

Рис. 3.4 Створення нового проекту

У полі Name задаємо ім'я проекту -- FirstForm і зберігаємо його в теку, визначувану полем Location. Одержану теку ви зможете згодом перемістити на інший комп'ютер і продовжити роботу -- в ній знаходитимуться всі створювані нами файли цього проекту. На екрані з'явилася порожня Windows-форма.

Після того, як ми створили новий проект, можна побачити основні частини середовища розробки (Рис. 3.5).

Рис. 3.5 Головне вікно програми в режимі розробки

3.3 Вікно «Провідник проекту»

Вікно Solution Explorer (провідник проекту, View --> Solution Explorer, або поєднання клавіш Ctrl+Alt +L) містить компоненти, що входять до складу проекту. Пункти контекстного меню цього вікна (що викликається натисненням правої кнопки миші) дозволяють змінювати вміст проекту, а також додавати нові компоненти.

Рис. 3.6 Контекстне меню вікна Solution Explorer

При створенні нового проекту Solution Explorer містить компоненти, створені шаблоном.

Рис. 3.7 Компоненти, що входять до складу нового додатку

Каталог References містить посилання на класи, використовувані в проекті за умовчанням. Подвійне клацання миші на підкаталогах References запускає вікно Object Browser (провідник об'єктів, View --> Object Browser, або поєднання клавіш Ctrl+Alt+J). Вікно Object Browser, у свою чергу, є вичерпним засобом отримання інформації про властивості об'єктів. Так абстрактний клас brush успадковується від класу System.MarshalByRefObject і містить методи Clone, Dispose(bool), Dispose і Finalize.

Рис. 3.8 Вікно Object Browser

Можна одержувати короткий опис будь-якого методу, класу або властивості, просто клацнувши на ньому, -- на інформаційній панелі негайно відобразиться коротка довідка. Для досвідченого розробника Object Browser -- незамінний помічник в роботі, набагато зручніший, ніж довідка.

Файл App.ico містить зображення іконки, яке на формі розташоване у верхньому лівому кутку. Файл AssemblyInfo.cs містить інформацію про наш додаток. При створенні дистрибутива в цей файл поміщається інформація програми, використовувана в технічних цілях, а також цифровий ключ.

3.4 Вікно Class View

Вікно Class View -- (огляд класів, View --> Class View, або поєднання клавіш Ctrl+Shift+C), дозволяє переміщатися в коді по вибраному об'єкту; містить методи, класи, дані всього лістингу проекту. Для переходу, наприклад, в метод Main клацаємо на відповідній назві у вікні Class View.

Рис. 3.9 Вікно Class View. Дозволяє швидко переміщатися за кодом всього проекту

3.5 Вікно Properties Window

Вікно властивостей Properties -- основний інструмент настройки форми і її компонентів. Вміст цього вікна є всім списком властивостей вибраного в даний момент компоненту або форми. Викликається це вікно декількома способами -- в меню View вибираємо пункт Properties Window (або використовуємо клавішу F4), на вибраному об'єкті клацаємо правою кнопкою миші і в контекстному меню пункт Properties вибираємо об'єкт і натискаємо F4 або просто вибираємо об'єкт і переходимо у вікно Properties. Коли ми тільки створили проект, у вікні Properties відображаються властивості самої форми.

Рис. 3.10 Вікно властивостей Properties

3.6 Вікно панелі інструментів

Вікно Toolbox (панель інструментів, View --> Toolbox, або поєднання клавіш Ctrl+Alt+X) містить компоненти Windows-форм, звані також елементами управління, які розміщуються на формі. Воно складається з декількох закладок: My User Controls, Components, Data, Windows Forms і General:

Рис. 3.11 Вікно Toolbox

Закладкою, що найбільш часто вживається, є Windows Forms. Для розміщення потрібного елементу управління досить просто клацнути на ньому у вікні Toolbox або, схопивши, перетягнути його на форму. Перемикання виду значків дозволяє розмістити їх без смуги прокрутки.

Рис. 3.12 Представлення елементів у вигляді списку

Рис. 3.13 Представлення елементів у вигляді значків

У вікні Toolbox доступно відображення всіх закладок.

Рис. 3.14 Встановлюємо галочку "Показати всі закладки"

Рис. 3.15 Повний список закладок

Закладка My User Controls дозволяє зберігати власні списки елементів управління:

Рис. 3.16 Додавання закладки

Рис. 3.17 Власна закладка "Моя закладка для First Form"

Рис. 3.18 Відновлення значень за умовчанням

Створені таким чином закладки можна перейменувати або видалити, вибравши в контекстному меню пункти Rename Tab і Delete Tab відповідно.

Якщо в результаті всіх експериментів ми побачимо, що поточний вид вікна Toolbox сильно відрізняється від первинного, для відновлення значень за умовчанням виберіть в контекстному меню будь-якої закладки пункт Add/Remove Items. . У вікні, що з'явилося, натисніть на кнопку Reset. З'являється вікно попередження -- "Настройки Toolbox будуть відновлені. Всі призначені для користувача закладки будуть видалені. Продовжувати?" Погодившись з попередженням, ви побачите вид Toolbox за умовчанням.

Всі закладки, окрім Clipboard Ring і General, містять компоненти, які можна перетягнути на форму. Закладка Clipboard Ring є аналогом буфера обміну в Microsoft Office 2003, буфера, що відображає вміст, за декілька операцій копіювання або вирізування. Для вставки фрагмента достатньо двічі клацнути по ньому.

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

3.7 Режими дизайну і коду

При створенні нового проекту запускається режим дизайну -- форма є основою для розташування елементів управління. Для роботи з програмою слід перейти в режим коду. Це можна зробити декільком способами: клацнути правою кнопкою миші в будь-якій частині форми і в меню, що з'явилося, вибрати View Code, у вікні Solution Explorer зробити те ж саме на компоненті Form 1.cs або просто двічі клацнути на формі -- при цьому згенерується метод Form1_Load. Після хоч би одноразового переходу в режим коду в цьому проекті з'явиться вкладка Form1.cs*, натискаючи на яку, теж можна переходити в режим коду. Для переходу в режим коду також можна використовувати клавішу F7, а для повернення в режим дизайну -- поєднання Shift+F7.

Перемкнемося в режим коду і розглянемо деякі блоки.

Даний блок визначає, які простори імен використовуються в цьому проекті:

using System;

using System.Drawing;

using System.Collections;

using System.ComponentModel;

using System.Windows.Forms;

using System.Data;

Для проглядання інформації про вміст кожного з цих просторів можна скористатися вікном Object Browser.

Далі визначається власний простір імен, ім'я якого співпадає з назвою проекту:

namespace FirstForm

При необхідності цю назву можна міняти.

Клас форми Form1, успадкований від System.Windows.Forms.Form, містить в собі майже весь код:

public class Form1 : System.Windows.Forms.Form

{

... }

Усередині цього класу знаходиться конструктор форми:

public Form1()

{

//

// Required for Windows Form Designer support

//

InitializeComponent();

//

// TODO: Add any constructor code after InitializeComponent call

//

}

Подія Initiliaze відбувається у момент запуску додатку; код, що додається після InitializeComponent, може змінювати вміст форми або елементи управління у момент запуску.

Область Windows Form Designer generated code містить код графічного інтерфейсу елементів управління і форми, що автоматично генерується середовищем. Порожня форма містить опис розмірів і заголовка. Клацнемо на знак (+) для перегляду це області:

#region Windows Form Designer generated code

/// <summary>

/// Required method for Designer support -- do not modify

/// the contents of this method with the code editor.

/// </summary>

private void InitializeComponent()

{

this.components = new System.ComponentModel.Container();

this.Size = new System.Drawing.Size(300,300); // розмір форми в пікселях

this.Text = "Form1";// заголовок форми.

}

#endregion

Можна міняти значення параметрів, що створюються середовищем, і тоді зміни негайно відіб'ються на графічному інтерфейсі. Концепція області Windows Form Designer generated code схожа з концепцією WYSIWYG 1) редакторів HTML-коду, де можна розміщувати компоненти перетяганням, а середовище само генерує HTML-код.

Метод Main реалізує головну точку входу в програму -- тобто місце, звідки починається виконання написаного нами коду:

static void Main()

{

Application.Run(new Form1());

}

При відладці великих програм зручно використовувати нумерацію рядків, яку можна включити в пункті меню Tools/Options./Text Editor/C# -- на формі Display -- перемикач Line Numbers.

Рис. 3.20 Відображення нумерації рядків коду

При довгій роботі над кодом контрастні чорні букви на білому фоні викликають втому, тому бажано як фоновий колір встановити інший -- наприклад, сірий. Це можна зробити в Options на вкладці Environments/Font and Colors.

Рис. 3.21 Вкладка Environments/Font and Colors. Тут же можна змінити шрифт коду -- наприклад, встановити Times New Roman

В результаті режим коду приймає наступний вигляд:

Рис. 3.22 Ергономічний вид режиму коду

3.8 Властивості проекту

Розглянемо властивості проекту. У вікні Solution Explorer виділяємо назву проекту -- FirstForm, клацаємо правою кнопкою миші і вибираємо в меню пункт Properties. У вікні, що з'явилося, містяться всі властивості поточного проекту.

Рис. 3.23 Вікно Common Properties / General

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

Вкладка Common Properties / General включає наступні властивості:

Assembly Name -- назва збірки.

Output Type -- тип компільованого додатку. За умовчанням для Windows-додатків стоїть Windows Application.

Default Namespace -- назва простору імен в коді. За умовчанням співпадає з ім'ям проекту.

Startup Object -- назва класу, що містить точку входу в програму - метод Main.

Application Icon -- шлях до файлу з іконкою додатку.

Project File -- ім'я файлу з інформацією про проект. Знаходиться усередині каталогу з проектом;

Project Folder -- шлях до файлу з проектом.

Output File -- назва файлу, що створюється при компіляції, -- вихідного файлу. Співпадає з ім'ям проекту.

На вкладці Configuration Properties / Build розглянемо деякі властивості.

Рис. 3.24 Вікно Configuration Properties / Build

Optimize Code -- оптимізація програми, значення цієї властивості true може значно збільшити продуктивність додатку.

Allow Unsafe Code Blocks -- вирішити використання ключового слова unsafe в коді проекту.

Warning Level -- рівень попереджень, що відображаються при компіляції програми.

Treat Warnings As Errors -- сприймати всі попередження як помилки. Якщо оголосити змінну в коді, але ніде не використовувати її, при значенні цієї властивості False додаток скомпілюється, при значенні True -- ні.

Output Path -- шлях, де формується вихідний файл. Тека bin знаходиться усередині теки проекту.

Generate Debugging Information -- виводити інформацію при відладці. Ця властивість повинна бути включена: саме ці повідомлення допомагають виправляти код.

3.9 Компіляція програми

Для перевірки програми використовуються два способи відладки. Перший спосіб -- Build Solution, який перевіряє код і компілює програму, не запускаючи її. Це дуже зручно, коли ви працюєте над окремим модулем великої розробки, і немає можливості перевіряти весь продукт в цілому. Для запуску цього способу вибираємо в головному меню пункт Build --> Build Solution (або поєднання клавіш Ctrl+Shift+B).

Рис. 3.25 Пункт головного меню Build

При цьому з'являється вікно Output, в якому виводиться інформація про всі стадії компіляції.

Рис. 3.26 Вікно Output, додаток не містить помилок

Якщо в коді є помилки, вікно Output виведе повідомлення про помилки, потім з'явиться їх список, причому для відладки достатньо двічі клацнути на відповідній помилці для переходу до потрібної ділянки коду:

Рис. 3.27 Вікно Output, в коді не вистачає фігурної дужки

Інший спосіб компіляції програми -- Debug, при якому перевіряється код, компілюється програма і формується призначений для користувача інтерфейс.

Рис. 3.28 Пункт головного меню Debug

Для запуску цього способу натискаємо клавішу F5. На екрані знову з'являється вікно Output, що інформує нас про хід компіляції. Якщо додаток не містить помилок, то на екрані з'явиться готова форма.

При запуску додатку в каталозі bin\Debug усередині каталогку проекту виникає файл FirstForm.exe і файли, необхідні для відладки. Файл FirstForm.exe і є готовий додаток. Готовий додаток для розповсюдження необхідно скомпілювати в режимі Release -- тоді з'явиться каталог bin\Release, яка міститиме тільки FirstForm.exe. Ми можемо просто скопіювати його на інший комп'ютер, і якщо там є .NET Framework, все працюватиме.

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

Яка різниця між компіляціями Build і Debug? Припустимо, що ми розробляємо додаток, який підключатиметься до бази даних на видаленому комп'ютері, недоступному у момент розробки. Додаток одержуватиме дані відразу ж при запуску. Для відладки коду програми зручніше використовувати режим Build, оскільки відладка в режимі Debug супроводжуватиметься повідомленнями про помилки, що виникають із-за неможливості підключення до іншого комп'ютера. Саме підключення також займатиме якийсь час.

Якщо ж ми розробляємо локальний додаток, режим відладки Debug є зручнішим. Далі, коли ми запускатимемо додатки, матися на увазі буде саме цей режим.

4. Експериментальне дослідження та опис програмної реалізації

4.1 Порівняльний аналіз технологій проектування мережевих додатків

4.1.1 Створення мережевих додатків на Delphi з використанням Windows Sockets API

У Delphi існують вбудовані класи для роботи з мережею - це компоненти Delphi на закладці internet (tserversocket і tСlientcocket) і компоненти fastnet, або компоненти indy в Delphi 7. Але зараз ми будемо розглядати програмування мережевих додатків на низькому рівні - з використанням winsock api.

Це потрібне для того, щоб:

1. У випадку, якщо для додатку критичний розмір (це найбільше відноситься до серверних додатків, які найчастіше не мають ніякої візуальної частини), те використання будь-яких vcl-компонентів украй небажано.

2. Програмування на нижчому рівні традиційно вимагає великих витрат, але надає повніший контроль за роботою додатку.

3. І, нарешті, знання основ роботи windows socket необхідне всім охочим розробляти мережеві додатки і буде хорошою практикою для повнішого розуміння всіх процесів, що відбуваються.

Для підтримки мережевих додатків існує технологія, названа "сокети". Сокет - це модель одного кінця з'єднання, зі всіма властивими йому властивостями і методами. По суті, це прикладний програмний інтерфейс, що входить до складу багатьох операційних систем (ОС) і покликаний для підтримки мережевих можливостей ОС. У стандарті структури протоколів семирівневої моделі osi-сокети лежать на так званому транспортному рівні, нижче знаходиться мережевий протокол ip, а вище - протоколи сеансового рівня, такі як ftp pop3, smtp і т.д.

У windows підтримка сокетів включена починаючи з версії 3.11 і названа winsock. Для написання додатків з мережевою підтримкою існує спеціальний winsock api.

Сокети можуть базуватися на tcp/ip, ipx/spx але надалі ми говоритимемо тільки про з'єднання tcp/ip.

Всі мережеві додатки побудовані на технології сервер клієнта; це означає, що в мережі існує принаймні один додаток, що виявляє сервером, типове завдання якого - це очікування запиту на підключення від додатків-клієнтів, яких може бути теоретично скільки завгодно, і виконання всіляких процедур у відповідь на запити клієнтів. Для клиент-серверной технології абсолютно неважливо, де розташовані клієнт і сервер - на одній машині або на різних. Звичайно, для успішного з'єднання клієнта з сервером клієнту необхідно мати мінімальний набір даних про розташування сервера - для мереж tcp/ip це ip-адреса комп'ютера, де розташований сервер, і адреса порту, на якому сервер чекає запити від клієнтів.

Кожний з комп'ютерів в мережі tcp/ip має свою унікальну ip-адресу, яка використовується для обміну даними з іншими комп'ютерами. Кожен посиланий пакет від одного комп'ютера іншому має адресу відправника і одержувача, що дозволяє його однозначно ідентифікувати. Проте у випадку, якщо на комп'ютері працює безліч додатків, що одночасно використовують мережу, то такого набору атрибутів явно недостатньо.

Для дозволу неоднозначності окрім адреси кожне з'єднання на кожному кінці має ідентифікатор під назвою "порт", цей ідентифікатор представляє число від 0 до 65535. Таким чином, пара адрес+порт є сокетом-каналом, по якому два комп'ютери обмінюються даними один з одним. Тільки один додаток на одному комп'ютері в один і той же час може використовувати конкретний порт, проте для серверних частин можливо створення декількох сокетів на одному порту для роботи з декількома клієнтами.

Значення порту не обов'язково повинне співпадати на сервері і клієнті - клієнту для з'єднання важливо тільки знати порт сервера, порт клієнта може вибиратися клієнтом довільно і стає відомий серверу у момент запиту клієнта на з'єднання. Коли з'єднання буде встановлено, ОС створить для серверного додатку відповідний сокет, з яким і працюватиме додаток, так що порт клієнта для сервера абсолютно не важливий.

Механізм роботи сокетів такий: на серверній стороні запускається серверний сокет, який після запуску відразу переходить в режим прослуховування (тобто очікування з'єднання клієнтів). На стороні клієнта створюється сокет, для якого указується ip-адреса і порт сервера і дається команда на з'єднання. Коли сервер одержує запит на з'єднання, ОС створює новий екземпляр сокета, за допомогою якого сервер може обмінюватися даними з клієнтом. При цьому сокет, який створений для прослуховування, продовжує знаходитися в режимі прийому з'єднань, таким чином програміст може створити сервер, що працює з декількома підключеннями від клієнтів.

Робота з сокетами, по суті, це операції введення-висновку, які синхронні і асинхронні. У термінології сокетів робота в асинхронному режимі називається блокуючими сокетами, а в синхронному - неблокуючі сокети. Спроба з'єднання або прийому даних в блокуючому режимі (відправка завжди синхронна, оскільки фактично є постановкою в чергу) означає, що поки програма не з'єднається або не прикмет дані, передачі управління на наступного оператора не відбудеться.

Тепер розглянемо мінімальний набір функцій з winsock api, необхідних для написання елементарного клієнта і сервера. Самі функції знаходяться у файлі winsock.dll. Файл winsock.pas містить необхідні оголошення функцій winsock api і базові структури даних, що імпортуються. На жаль, цей файл імпортує не всі необхідні нам функції, і пізніше ми напишемо свій файл імпорту.

function wsastartup(wversionrequired: word; var wsdata: twsadata): integer; stdcall;

Функція повідомляє ОС, що в будь-якому процесі додатку можуть бути використані функції winsock. Функція повинна бути викликана один раз при запуску додатку перед використанням будь-якої функції winsock.

function wsacleanup: integer; stdcall;

Функція повідомляє ОС, що додаток більш не використовує winsock. Повинна бути викликана перед завершенням додатку.

function socket(af, struct, protocol: integer): tsocket; stdcall;

Функція створює сокет. Порт і адреса задається у функції bind (сервер) або connect (клієнт). Вхідний параметр af - специфікація сімейства сокетів (af_inet, af_ipx і ін.), struct - специфікація типу нового сокета (приймає значення sock_stream або sock_dgram), protocol - специфічний протокол, який використовуватиметься сокетом. Якщо функція виконана без помилок, вона повертає дескриптор на новий сокет, якщо помилки є, повертається invalid_socket.

function connect(s: tsocket; var name: tsockaddr; namelen: integer): integer; stdcall;

Функція з'єднання для клієнта. Структура адреси містить порт (необхідно привести функцією htons) і адресу (для клієнта необхідно привести з імені або специфікації ip4 - xxx.xxx.xxx.xxx).

function bind(s: tsocket; var addr: tsockaddr; namelen: integer): integer; stdcall;

Функція асоціює адресу з сокетом. Структура адреси містить порт (необхідно привести функцією htons) і адресу (для сервера звичайно указується inaddr_any - будь-який).

function send(s: tsocket; var buf; len, flags: integer): integer; stdcall;

Функция отправки данных. Помещает в очередь сокета s кусок данных из buf, длиной len. Последний параметр отвечает за вид передачи сообщения. Может быть проигнорирован (0).

function recv(s: tsocket; var buf; len, flags: integer): integer; stdcall;

Функція отримання даних.

Отже, розглянемо приклади елементарного сервера і клієнта. Домовимося, що сервер працюватиме в асинхронному (блокуючому режимі). Єдина функціональність сервера - це отримання рядків даних від клієнта і висновок їх на екран. Зв'язок клієнта з сервером розривається після отримання рядка, що складається з єдиного символу 'q'.

Для забезпечення можливості підключення до сервера безлічі клієнтів сервер на кожне з'єднання запускає окремий потік.

program winsock_server; //Простейшее додаток-сервер. //Сокеты працюють в блокуючому режимі. //На кожне з'єднання створюється окремий потік. $apptype console}uses sysutils, winsock, windows; var vwsadata : twsadata; vlistensocket,vsocket : tsocket; vsockaddr : tsockaddr; trid : thandle; const cport = word(33); csigexit = 'q'; //Процедура окремого потоку для кожного клієнта. procedure socketthread; var sockname : tsockaddr; abuf : array of char; vbuf : string; vsize : integer; s :tsocket; bufsize : integer; begin s := vsocket; if s = invalid_socket then exit; vsize := sizeof(tsockaddr); getpeername(s, sockname, vsize); writeln(format('client accepted, remote address [%s].',[inet_ntoa (sockname.sin_addr)])); //Определяем розмір буфера читання для сокета vsize := sizeof(bufsize); getsockopt(s,sol_socket,so_rcvbuf,pchar(@ bufsize),vsize); writeln(format('receive buffer size [%d]',[bufsize])); setlength(abuf,bufsize); repeat //Получаем дані. Процедура працює в блокуючому режимі, //таким чином наступний рядок коду не одержить управління, //пока не поступлять дані від клієнта. vsize := recv(s,abuf[0],bufsize,0); if vsize

4.1.2 Створення мережевих додатків з використанням dotNET Remoting C#

Розглянемо простий додаток, що полягає, як і належить, з сервера, клієнта і випробовуваного об'єкту.

Як сервер цілком підійде звичайне консольне .NET-приложение, початковий текст якого приведений нижче:

// Server.cs

using System;

using System.Runtime.Remoting;

namespace Server

{

class Server

{

[STAThread]

static void Main(string[] args)

{

RemotingConfiguration.Configure("Server.exe.config");

Console.WriteLine("Press Enter to exit");

Console.ReadLine();

}

}

}

Сервером цю програму робить всього лише одна виділена в лістингу строчка, яка викликає процедуру конфігурації підсистеми Remoting. Для цього вона використовує наступний конфігураційний файл:

<!-- App.config -->

<configuration>

<system.runtime.remoting>

<application name="RemotingTest">

<service>

<wellknown

mode="SingleCall"

type="TestObject.Test, TestObject"

objectUri="Test.rem" />

</service>

<channels>

<channel ref="tcp" port="8008" />

</channels>

</application>

</system.runtime.remoting>

</configuration>

Імена того конфігураційного файлу, який спользуются в програмі, і того, який ми створюємо в Visual Studio, розрізняються. Під час збірки проекту Visual Studio копіює файл App.config з каталога проекту в цільовий каталог програми і перейменовує його за правилами ІмяПрограмми.exe.config. У нашому випадку це буде Server.exe.config.

Також нам буде просто необхідний сам тестований об'єкт. Ось він:

// TestObject.cs

using System;

namespace TestObject

{

public class Test: MarshalByRefObject

{

public string GetAppName()

{

return AppDomain.CurrentDomain.FriendlyName;

}

}

Тут ключовим моментом є спадкоємство від класу MarshalByRefObject. Цього достатньо для можливості видаленого використання екземпляра такого класу.

Наш об'єкт є dll-модулем і повертатиме назву тієї програми, в якій він завантажений. Це дозволить легко визначати, де в даний момент працює об'єкт - на клієнті або на сервері.

А зараз розглянемо клієнт:

// Client.cs

using System;

using System.Runtime.Remoting;

using TestObject;

namespace Client

{

class Client

{

[STAThread]

static void Main(string[] args)

{

RemotingConfiguration.Configure("Client.exe.config");

Test test = new Test();

Console.WriteLine(test.GetAppName());

}

}

}

Так само, як і у випадку з сервером, для конфігурації ми використовуватимемо файл:

<!-- App.config -->

<configuration>

<system.runtime.remoting>

<application>

<client>

<wellknown

type="TestObject.Test, TestObject"

url="tcp://localhost:8008/RemotingTest/Test.rem" />

</client>

</application>

</system.runtime.remoting>

</configuration>

Після збірки всіх модулів запустите сервер, а потім клієнта. Якщо ви всі зробили правильно, клієнт повинен вивести на екран наступну строчку:Server.exe

Це говорить про те, що домен, в якому виконується об'єкт - сервер. Тепер зрадимо одну строчку у файлі Client.exe.config:

<!--- Client.exe.config -->

<configuration>

<system.runtime.remoting>

<application>

<client>

<wellknown

type="TestObject.Test1, TestObject"

url="tcp://localhost:8008/RemotingTest/Test.rem" />

</client>

</application>

</system.runtime.remoting>

</configuration>

Тобто тепер об'єкт запускається на стороні клієнта, хоча код програми ми не міняли.

4.2 Опис інтерфейсу користувача системи та логіко-функціональной схеми системи.

Рис. 4.1 Логіко-функциональна схема

Робоче вікно програми розділене на 2 частини.

Рис. 4.2 Головне вікно програми

У лівій частині розташований список RSS-каналов . При подвійному клацанні по вибраному каналу відкривається список, що містить заголовки новин даного каналу (рис. 4.3). При цьому в правій частині вікна відображується вміст вибраної новини (рис. 4.4).

Рис. 4.3 Заголовки новин даного каналу

Рис. 4.4 Вміст вибраної новини

У системі також передбачена панель навігації (рис. 4.5), яка дозволяє здійснювати швидкий перехід від списку новин до списку каналів, а також можливість додавання і видалення каналів із списку.

Рис. 4.5 Панель навігації

При натисненні кнопки додавання нового новинного каналу з'являється форма з полями заслання і імені каналу (рис. 4.6).

Рис. 4.6 Форма додавання новинних каналів

При натисненні кнопки видалення новинного каналу з'являється діалогове вікно з питанням про підтвердження видалення .

Рис. 4.7 Діалог підтвердження видалення

Кнопка «Оновлення» дозволяє завантажити свіжі новини, які позначаються жирним шрифтом.

Пошук, передбачений в системі (Мал. 4.10), дозволяє, знайти потрібну нам новину, задавши строковий фрагмент, який в ній міститься .

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

4.3 Програмна частина. Читання новини

При запуску програми відразу після ініціалізації компонентів інтерфейсів запускається функція load1 ():

private void Load1 ()

{

cur_post = 0;

listView1 .Items.Clear();

feedR f = new feedR ();

List<Dictionary<string , string> > feed_list = f.getFeedsList();

for (int i = 0; i < feed_list .Count; i++ )

{

Dictionary<string , string > feedsProp = feed_list [i];

string name = feedsProp ["name "];

int db_id = Convert .ToInt32(feedsProp ["db_id "]);

string url = feedsProp ["url "];

//listBox1 .Items.Add(name );

listView1 .Items.Add(name ).Tag = db_id + "## " + url ;

int count_unread = f.GetReedCount(db_id );

if (count_unread > 0)

{

listView1 .Items[i].Font = new Font (listView1 .Items[i].Font, FontStyle .Bold);

listView1 .Items[i].Text += " (" + count_unread + ")";

}

listView1 .Items[i].ImageIndex = 0;

}

}

Функція load () використовуючи метод класу fids , який знаходиться в бібліотеці програми feedR_dll .dll, getFeedsList отримує список каналів новин :

public List<Dictionary<string , string> > getFeedsList ()

{

List<Dictionary<string , string> > feed_list = new List<Dictionary<string , string >>();

using (SQLiteConnection cn = new SQLiteConnection (connectionString ))

{

using (SQLiteCommand cmd = cn .CreateCommand())

{

cmd .CommandText = "SELECT name , url , id FROM feeds ORDER by id ASC ;";

cmd .CommandType = CommandType .Text;

cn .Open();

SQLiteDataReader dr = (SQLiteDataReader )cmd .ExecuteReader();

while (dr .Read())

{

Dictionary<string , string > feed = new Dictionary<string , string >();

feed .Add("name ", dr ["name "].ToString());

feed .Add("db_id ", dr ["id "].ToString());

feed .Add("url ", dr ["url "].ToString());

//SQLiteCommand cmd2 = cn .CreateCommand();

//cmd2 .CommandText = "SELECT count (id ) from feeds_content WHERE feed_id="+dr ["id "]+" AND reed=0 ";

//cmd2 .CommandText = "SELECT count (id ) from feeds_content WHERE feed_id= " + dr ["id "];

feed_list .Add(feed );

}

}

}

return feed_list ;

}

Після подвійного клацання на вибраний канал новин список оновлюється і замість імен новинних каналів з допомогою метод getPosts класу fidR , виводиться список всіх новин вибраного новинного каналу.

public List<Dictionary<string , string> > getPosts (int feed_id )

{

List<Dictionary<string , string> > posts = new List<Dictionary<string , string >>();

using (SQLiteConnection cn = new SQLiteConnection (connectionString ))

{

using (SQLiteCommand cmd = cn .CreateCommand())

{

cmd .CommandText = "SELECT id,title,reed,link FROM feeds_content WHERE feed_id= '" + feed_id + "' ORDER by utime DESC ;";

cmd .CommandType = CommandType .Text;

cn .Open();

SQLiteDataReader dr = (SQLiteDataReader )cmd .ExecuteReader();

while (dr .Read())

{

Dictionary<string , string > post = new Dictionary<string , string >();

post .Add("title ", dr ["title "].ToString());

post .Add("db_id ", dr ["id "].ToString());

post .Add("reed ", dr ["reed "].ToString());

post .Add("link ", dr ["link "].ToString());

posts .Add(post );

}

}

}

return posts ;

}

Функція використовує вище описаний метод і що перебудовує список приведена нижче:

private void listView1_ItemActivate (object sender , EventArgs e)

{

ListView lv = (ListView )sender ;

string[ ] text ;

string[ ] separator = { "## " };

string tag = lv .SelectedItems[0].Tag.ToString();

text = tag .Split(separator , StringSplitOptions .RemoveEmptyEntries);

//webBrowser1 .DocumentText = "id = " + text [0]+ "<br>url = " + text [1];

feedR f = new feedR ();

if (cur_feed_id == 0)

{

listView1 .Items.Clear();

//Типа собсно фид

List<Dictionary<string , string> > posts = f.getPosts(Convert .ToInt32(text [0]));

for (int i = 0; i < posts .Count; i++ )

{

listView1 .Items.Add(posts [i]["title "]).Tag = posts [i]["db_id "];

int reed = Convert .ToInt32(posts [i]["reed "]);

if (reed == 0)

{

listView1 .Items[i].Font = new Font (listView1 .Items[i].Font, FontStyle .Bold);

}

listView1 .Items[i].ImageIndex = 1;

}

cur_feed_id = Convert .ToInt32(text [0]);

cur_post = 0;

toolStripButton1 .Enabled = true ;

listView1 .Columns[0].Width = listView1 .Width - 25;

}

}

При навігації за отриманим списком новин в праву частину інтерфейсу користувача видається вміст вибраної новини за допомогою методу getFeedContent класу fidR , яка приймає аргументом id поточної новини. При читанні ж новини, яка була не прочитана, окрім її виводу на екран, за допомогою методу setReed класу fidR новина позначається як прочитана.

blic Dictionary<string , string > getFeedContent (int post_id )

{

Dictionary<string , string > post = new Dictionary<string , string >();

using (SQLiteConnection cn = new SQLiteConnection (connectionString ))

{

using (SQLiteCommand cmd = cn .CreateCommand())

{

cmd .CommandText = "SELECT * FROM feeds_content WHERE id= '" + post_id + "' LIMIT 0,1;";

cmd .CommandType = CommandType .Text;

cn .Open();

SQLiteDataReader dr = (SQLiteDataReader )cmd .ExecuteReader();

dr .Read();

post .Add("title ", dr ["title "].ToString());

post .Add("guid ", dr ["guid "].ToString());

post .Add("link ", dr ["link "].ToString());

post .Add("author ", dr ["author "].ToString());

post .Add("pubDate ", dr ["pubDate "].ToString()); //по ходу буде не потрібний

post .Add("printDate ", this .UnixTimeToDT((int )dr ["utime "]).ToString());

post .Add("description ", dr ["description "].ToString());

}

}

return post ;

}

public bool setReed (int id ) //id - post

{

try

{

using (SQLiteConnection cn = new SQLiteConnection (connectionString ))

{

using (SQLiteCommand cmd = cn .CreateCommand())

{

cmd .CommandText = "UPDATE feeds_content SET reed=1 WHERE id= " + id ;

cmd .CommandType = CommandType .Text;

cn .Open();

cmd .ExecuteNonQuery();

cn .Close();

}

}

}

catch

{

return false ;

}

return true ;

}

Пошук

Пошук, після попередньої обробки запиту, здійснюється за допомогою методу Search класу fidR , який очищає рядок пошуку від спеціалізованих символів і розділових знаків, розбиває рядок на слова, здійснює пошук по базі даних і повертає результат пошуку.

private void search ()

{

if ((textBox1 .Text.Length > 3) && (textBox1 .Text != "Пошук.."))

{

feedR f = new feedR ();

List<Dictionary<string , string> > posts = f.Search(textBox1 .Text);

if (posts .Count != 0)

{

listView1 .Items.Clear();

for (int i = 0; i < posts .Count; i++ )

{

listView1 .Items.Add(posts [i]["title "]).Tag = posts [i]["db_id "];

int reed = Convert .ToInt32(posts [i]["reed "]);

if (reed == 0)

{

listView1 .Items[i].Font = new Font (listView1 .Items[i].Font, FontStyle .Bold);

}

listView1 .Items[i].ImageIndex = 1;

}

cur_feed_id = 255000;

cur_post = 0;

toolStripButton1 .Enabled = true ;

listView1 .Columns[0].Width = listView1 .Width - 25;

}

else

{

MessageBox .Show("Нічого не знайдено", "Увага!", MessageBoxButtons .OK, MessageBoxIcon .Information);

}

}

}

private string clean_words (string value )

{

string[ ] drop_char = { };

string[ ] drop_words = { "a" , "the ", "of ", "and ", "or ", "for ", "this " };

for (int i = 0; i < drop_char .Length; i++ )

{

value = value .Replace(drop_char [i], "");

}

return value ;

}

public List<Dictionary<string , string> > Search (string search_str )

{

List<Dictionary<string , string> > posts = new List<Dictionary<string , string >>();

search_str = clean_words (search_str );

string[ ] search_text ;

string[ ] separator = { " " };

string tag = search_str ;

search_text = tag .Split(separator , StringSplitOptions .RemoveEmptyEntries);

string select = "SELECT id,title,reed,link FROM feeds_content WHERE ";

string added_q = "";

for (int i = 0; i < search_text .Length; i++ )

{

if (search_text [i].Length > 2)

{

if (added_q .Length == 0)

{

added_q += " (title like '%" + search_text [i]+ "% ' OR description like '%" + search_text [i]+ "% ')";

}

else

{

added_q += " OR (title like '%" + search_text [i]+ "% ' OR description like '%" + search_text [i]+ "% ')";

}

}

}

select += added_q+ " ORDER by id ASC ;";

using (SQLiteConnection cn = new SQLiteConnection (connectionString ))

{

using (SQLiteCommand cmd = cn .CreateCommand())

{

cmd .CommandText = select ;

cmd .CommandType = CommandType .Text;

cn .Open();

SQLiteDataReader dr = (SQLiteDataReader )cmd .ExecuteReader();

while (dr .Read())

{

Dictionary<string , string > post = new Dictionary<string , string >();

post .Add("title ", dr ["title "].ToString());

post .Add("db_id ", dr ["id "].ToString());

post .Add("reed ", dr ["reed "].ToString());

post .Add("link ", dr ["link "].ToString());

posts .Add(post );

}

}

}

return posts ;

}

Оновлення стрічки новин.

Оновлення новинних стрічок відбувається за допомогою методу updateFeed класу feedR .

public string updateFeed (int feed_id , string url )

{

HttpWebRequest request = (HttpWebRequest )WebRequest .Create(url );

HttpWebResponse response = null ;

try

{

response = (HttpWebResponse )request .GetResponse();

}

catch

{

}

StreamReader reader = new StreamReader (response .GetResponseStream(), Encoding .GetEncoding(response .CharacterSet));


Подобные документы

Работы в архивах красиво оформлены согласно требованиям ВУЗов и содержат рисунки, диаграммы, формулы и т.д.
PPT, PPTX и PDF-файлы представлены только в архивах.
Рекомендуем скачать работу.