|
|
|
|
В очередной раз Apache убрал со своего сайта бинарники посим качать приходится откуда прийдется:
http://apache.ip-connect.vn.ua/httpd/binaries/win32
(Раздел “Downloading Apache for Windows”)
Далее:
В моем случае это был httpd-2.2.31-x86. Причем версия сервера должна быть потокобезопасна.
В моем случае пришлось отключить модули ssl, прописать корневую дирректорию и порт.
Впринципе достаточно трёх комманд:
|
1 |
httpd -k install |
|
1 |
httpd -k start |
|
1 |
httpd -k stop |
В браузере идем на корень установленного сервера. Должны увидеть нечто без ошибки.
Расписывать не буду. ПОсле установки у нас есть порт, хост, имя пользователя и пароль. Это надо для дальнейшей настройки.
Для вышеуказанного web-сервера я скачивал версию php-5.2.17-Win32-VC6-x86. Здесь тоже важна потокобезопасность, так что необходимо быть внимательным.
|
1 2 3 4 5 6 |
LoadModule php5_module "C:/php/php5apache2_2.dll" PHPIniDir "C:/php" <IfModule mod_mime.c> AddType application/x-httpd-php .php AddType application/x-httpd-php-source .phps </IfModule> |
переименовываем файл php.ini и включаем модули для поддержки MySQL
|
1 2 |
extension=php_mysql.dll extension=php_mysqli.dll |
проверить включены ли модули можно коммандой
|
1 |
php -m |
После изменениий конфигурации не забываем перегружать web-сервер.
В папке htdocs я создал файлик hello.php со следующим содержимим и ходил на него из браузера
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
<html> <head> <title>Test PHP</title> </head> <body> <?php echo '<p>Hello world!</p>'; ?> <?php phpinfo() ?> <? $connect=mysql_connect("localhost","root","password") or die("Unable to Connect"); mysql_select_db("dbname") or die("Could not open the db"); $showtablequery="SHOW TABLES FROM dbname"; $query_result=mysql_query($showtablequery); while($showtablerow = mysql_fetch_array($query_result)) { echo $showtablerow[0]." "; } ?> </body> </html> |
Собсно здесь все вкратце описано
Сегодня я покажу, как добавить Sitemap.xml в Google и Яндекс. Напомню, что файл Sitemap – это карта сайта в формате XML для поисковиков, которая не видна посетителям блога. Она содержит список страниц сайта, которые должны быть проиндексированы поисковыми роботами, информацию о степени их важности и частоте обновления. Создание такой карты сайта помогает улучшить внутреннюю SEO оптимизацию сайта.
Подробнее можно почитать в моей статье, где описано, как создать карту сайта Sitemap.xml и зачем она нужна на блоге WordPress.
Чтобы добавить файл Sitemap в Google и Яндекс, надо, прежде всего, его создать. Далее добавляем сайт в панели для вебмастеров Яндекса и Гугла и подтверждаем права на сайт. Если Вы этого еще не сделали, то ранее я писал, как добавить сайт в Яндекс.Вебмастер и как добавить блог в Google Webmasters Tools.
Теперь переходим непосредственно к добавлению карты сайта в поисковики. Сообщить поисковым системам о наличии файла Sitemap можно двумя способами:
Даже если у Вас уже прописаны пути к карте сайта в robots.txt, выполнение второго способа будет совсем не лишним.
Заходим в панель Яндекс.Вебмастер по ссылке http://webmaster.yandex.ua/, предварительно авторизовавшись. Выбираем в списке добавленных сайтов тот, чей файл Sitemap хотим добавить в Яндекс. В левом меню “Общая информация” выбираем пункт “Настройка индексирования” – “Файлы Sitemap“. На открывшейся странице в специальное поле вводим полный путь к карте сайта и нажимаем кнопку “Добавить“.
Теперь карта сайта XML добавлена в поисковик Яндекс и файл Sitemap будет находиться в обработке около двух недель.
Если все сделано правильно, то через время можно будет наблюдать такую картину:
Как видите, я добавил в Яндекс два файла: Sitemap.xml и Sitemap.xml.gz. Второй – это запакованный XML-файл, сгенерированный плагином для WordPress Google XML Sitemaps. Думаю, сжатый файл Sitemap добавлять в Яндекс не обязательно, так как при нажатии на любую из кнопок “Подробнее“, можно увидеть совершенно одинаковую информацию.
Я оставил добавленными оба файла Sitemap, так как индексация блога проходит без проблем, и не вижу смысла что-то менять.
Если потребуется удалить карту сайта, нажмите на крестик напротив названия файла (см. предыдущий рисунок).
Здесь все делаем аналогично. Авторизуемся в Гугл и входим в Инструменты для вебмастеров по ссылке https://www.google.com/webmasters/tools/. Выбираем из списка нужный сайт и в левом меню выбираем пункт “Конфигурация сайта” – “Файлы Sitemap“. Нажимаем кнопку “Добавление/Проверка файла Sitemap“.
Появится всплывающее окно, где вводим адрес карты сайта и нажимаем “Отправить файл Sitemap“. Обратите внимание, что адрес http://blogibiznes.ru/ уже автоматически подставлен и надо дописать только недостающую часть.
Далее нажимаем “Обновите страницу“.
Как видим, добавить Sitemap.xml в Google и получить информацию о нем можно быстрее, чем в Яндекс.
Точно также, при необходимости, делается проверка файла Sitemap в Гугл. Только для этого надо будет нажать кнопку “Проверить файл Sitemap” во всплывающем окне.
Если при добавлении XML-файлов в Google возникли ошибки, удалите файлы из списка (см. рисунок выше) и попробуйте загрузить их вновь.
Добавить Sitemap.xml в Яндекс и Google надо один раз. Теперь при появлении новых статей на блоге поисковики точно не пропустят их при индексации, а сам процесс будет происходить быстрее. Карта сайта автоматически обновляется в панелях вебмастеров Яндекса и Гугла. Поэтому добавлять каждый раз новый файл Sitemap не надо.
Как видите, ничего сложного. Однако многие просто забывают добавить карту сайта XML в поисковики.
Java коллекции, наверное, наиболее распространенные сущности с которыми работает программист. Причем в завасимости от области разработки варьируется также и глубина осознания реализации той коллекции с которой работает разработчик. К примеру, в web разработке очень часто та или иная коллекция используется как промежуточная структура данных, целью которой является передать данные из DAO уровня в сервис или UI. Для многих опытных инженеров даже отсутствует разница между ArrayList и LinkedList, поскольку и та и другая структура полностью удовлетворяют его нуждам и нет причин использовать преимущества одной из них.
И в общем то хорошо все как-бы. Есть коллекции – бери любую работай и проблем не знай. Кабы вот на собеседованиях не пытали бесполезными вопросами. Да и в приграммировании низкоуровневых алгоритмов без них никуда, иногда за счет просаживания по перфомансу алгоритм может просто не взлететь и тогда уж очень важны становятся те “мелочи” на которые не обращаешь внимания изначально. Сюда же как следствие можно добавить модное сейчас направление “биг дата”, где очень пригодятся знания о всякоразных ньюансах и особенностях Java Collections Framework.
Давайте постараемся бегло рассмотреть общую структуру Java коллекций дабы получить общее представление об оных.
Для начала упомянем что Java Collections Framework не единственный фреймворк предоставляющий возможность работы с коллекциями вот еще некоторые:
1. Guava (Google Collections Library) – Библиотека добавляет несколько полезных реализаций структур данных, таких как мультимножество, мультиотображение и двунаправленное отображение. Улучшена эффективность.
2. Trove library – Реализация коллекций, позволяющая хранить примитивы (в Java Collections Framework примитивы хранить нельзя, только сущности унаследованные от класса Object), что позволяет повысить эффективность работы.
3. PCJ (Primitive Collections for Java) – так же как и Trove предназначены для примитивных типов, что позволит повысить эффективность.
4. Наконец Вы сами можете написать собственную коллекцию (тот же связной список). Иногда бизнес логика может затребовать существования некоего объекта, который должен частично реализовывать функционал коллекции. Так что опыт работы может здесь пригодится.
Как видим, выбрать есть из чего. Но для начала необходимо освоить базовые коллекции Java которыми пользуются чаще всего. К тому же некоторые сторонние библиотеки реализуют интерфейсы Java Collections Framework (пример Guava). То есть знание иерархии классов базовых коллекций позволит более быстро освоить сторонние библиотеки.
В библиотеке коллекций Java существует два базовых интерфейса, реализации которых и представляют совокупность всех классов коллекций:
1. Collection – коллекция содержит набор объектов (элементов). Здесь определены основные методы для манипуляции с данными, такие как вставка (add, addAll), удаление (remove, removeAll, clear), поиск (contains)
2. Map – описывает коллекцию, состоящую из пар “ключ — значение”. У каждого ключа только одно значение, что соответствует математическому понятию однозначной функции или отображения. Такую коллекцию часто называют еще словарем (dictionary) или ассоциативным массивом (associative array). Никак НЕ относится к интерфейсу Collection и является самостоятельным.
Хотя фреймворк называется Java Collections Framework, интерфейс Map и его реализации входят во фреймворк также!
Интерфейсы Collection и Map являются базовыми, но они не есть единственными. Их расширяют другие интерфейсы, добавляющие дополнительный функционал. О них мы ещё поговорим.
Итак, что же порождает Collection? Как видно с диаграммы, интерфейс Collection не является базовым. Он расширяет интерфейс Iterable, у которого есть только один метод iterator(). Это значит что любая коллекция будет возвращать итератор а также ее можно без всяких трудностей использовать в конструкции foreach.
Итератор – объект, который абстрагирует за единым интерфейсом доступ к элементам коллекции. Итератор это паттерн позволяющий получить доступ к элементам любой коллекции без вникания в суть ее реализации.
Идем дальше. Как видим на рисунке, интерфейс Collection расширяют интерфейсы List, Set и Queue. Давайте рассмотрим зачем нужен каждый.
1. List – Представляет собой упорядоченную коллекцию, в которой допустимы дублирующие значения. Иногда их называют последовательностями (sequence). Элементы такой коллекции пронумерованы, начиная от нуля, к ним можно обратиться по индексу.
2. Set – описывает коллекцию, не содержащую повторяющихся элементов. Это соответствует математическому понятию множества (set).
3. Queue – очередь. Это коллекция, предназначенная для хранения элементов в порядке, нужном для их обработки. В дополнение к базовым операциям интерфейса Collection, очередь предоставляет дополнительные операции вставки, получения и контроля.
Красным на рисунке выделены интерфейсы, зеленым – абстрактные классы, а синим готовые реализации. Сразу заметим что здесь не вся иерархия, а только основная её часть.
Как видим на рисунке, между интерфейсом и конкретной реализацией коллекции существует несколько абстрактных классов. Это сделано для того, что бы вынести общий функционал в абстрактный класс, таким образом реализовать повторное использование кода.
ArrayList – пожалуй самая часто используемая коллекция. Он инкапсулирует в себе обычный массив, длина которого может увеличиваться при добавлении новых элементов. Так как ArrayList использует массив, то время доступа к элементу по индексу минимально (В отличии от LinkedList). При удалении произвольного элемента из списка, все элементы находящиеся «правее» смещаются на одну ячейку влево, при этом реальный размер массива (его емкость, capacity) не изменяется. Если при добавлении элемента, оказывается, что массив полностью заполнен, будет создан новый массив размером (n * 3) / 2 + 1, в него будут помещены все элементы из старого массива + новый, добавляемый элемент.
LinkedList – Двусвязный список. Это структура данных, состоящая из узлов, каждый из которых содержит как собственно данные, так и две ссылки («связки») на следующий и предыдущий узел списка. Доступ к произвольному элементу осуществляется за линейное время (но доступ к первому и последнему элементу списка всегда осуществляется за константное время — ссылки постоянно хранятся на первый и последний, так что добавление элемента в конец списка вовсе не значит, что прийдется перебирать весь список в поисках последнего элемента).
Если Вы хотите использовать HashSet для хранения объектов СВОИХ классов, то вы ДОЛЖНЫ переопределить методы hashCode() и equals(), иначе два логически-одинаковых объекта будут считаться разными по хеш-коду, так как при добавлении элемента в коллекцию будет вызываться метод hashCode() класса Object (который скорее-всего вернет разный хэш-код для ваших объектов).
Важно отметить, что класс HashSet не гарантирует упорядоченности элементов, поскольку процесс хеширования сам по себе обычно не порождает сортированных наборов. Если вам нужны сортированные наборы, то лучшим выбором может быть другой тип коллекций, такой как класс TreeSet.
LinkedHashSet – поддерживает связный список элементов набора в том порядке, в котором они вставлялись. Это позволяет организовать упорядоченную итерацию вставки в набор. То есть, когда идет перебор объекта класса LinkedHashSet с применением итератора, элементы извлекаются в том порядке, в каком они были добавлены.
TreeSet – коллекция, которая хранит свои элементы в виде упорядоченного по значениям дерева. TreeSet инкапсулирует в себе TreeMap, который в свою очередь использует сбалансированное бинарное красно-черное дерево для хранения элементов. TreeSet хорош тем, что для операций add, remove и contains потребуется гарантированное время log(n).
PriorityQueue – единственная прямая реализация интерфейса Queue (не считая LinkedList, который больше является списком, чем очередью).
Интерфейс Map соотносит уникальные ключи со значениями. Ключ — это объект, который вы используете для последующего извлечения данных. Задавая ключ и значение, вы можете помещать значения в объект карты. После того как это значение сохранено, вы можете получить его по ключу.
HashMap — основан на хэш-таблицах, реализует интерфейс Map. Ключи и значения могут быть любых типов, в том числе и null. Данная реализация не дает гарантий относительно порядка элементов. Больше можно почитать здесь.
LinkedHashMap – расширяет класс HashMap. Он создает связный список элементов в карте, расположенных в том порядке, в котором они вставлялись. Это позволяет организовать перебор карты в порядке вставки. То есть, когда происходит итерация по коллекционному представлению объекта класса LinkedHashMap, элементы будут возвращаться в том порядке, в котором они вставлялись. Вы также можете создать объект класса LinkedHashMap, возвращающий свои элементы в том порядке, в котором к ним в последний раз осуществлялся доступ. Рекомендуется почитать.
Небольшое замечание. Очень часто, как было уже означено, есть необходимость использовать список пар (ключ значение). И, по правде говоря, в Java не существует из коробки коллекции, которая бы позволила наполнить этот список и затем по нему пройтись. Выход казалось бы очевидный – создать кастомный класс пары (ключ, значение) и помещать такие объекты в любимый список. Но очень часто программисты для этого используют именно HashMap. Но тут есть два ньюанса. Во первых механизм хеширования. Для описанной задачи он явно излишний – ведь обходить нам надо весь список по порядку а не брать произвольный элемент изнутри. И во вторых порядок. Как было уже сказанно HashMap не гарантирует порядок хранения элементов. В отличие от LinkedHashMap. Посим как вывод, если вам нужен упорядоченный список пар – используйте LinkedHashMap.
TreeMap – красно-черное дерево реализующее интерфейс NavigableMap. Коллекция сортируется по естественному упорядочиванию (natural ordering) ее ключей или с помощью интерфейса Comparator который задается при создании коллекции. Эта имплементация гарантирует время доступа log(n) для следующих методов: containsKey, get, put и remove.
WeakHashMap – основан на хэш-таблицах, реализует интерфейс Map с так называемыми слабыми ключами (weak keys). Пара в данной коллекции автоматически будет удалена когда ссылка на ключ больше нигде не используется. Другими словами, нахождение объекта представленного ключем в данной коллекции не блокирует сборщик мусора от зачистки. После того как ключ будет зачищен вся пара будет удалена из коллекции.
Их еще называют “устаревшими”. Но я не нашел аннотации @Deprecated или каких-либо иных, которые бы запрещали их использование в коде.
Все методы Hashtable, Stack, Vector являются синхронизированными, что делает их менее эффективными в однопоточных приложениях.
Получить синхронизированные объекты коллекций можно с помощью статических методов synchronizedMap и synchronizedList класса Collections.
Map m = Collections.synchronizedMap(new HashMap());
List l = Collections.synchronizedList(new ArrayList());
Синхронизированные обрамления коллекций synchronizedMap и synchronizedList иногда называют условно потоко безопасными – все операции в отдельности потокобезопасны, но последовательности операций, где управляющий поток зависит от результатов предыдущих операций, могут быть причиной конкуренции за данные. Здесь более. Условная безопасность потоков, обеспечиваемая synchronizedList и synchronizedMap представляет скрытую угрозу – разработчики полагают, что, раз эти коллекции синхронизированы, значит, они полностью потокобезопасны, и пренебрегают должной синхронизацией составных операций. В результате, хотя эти программы и работают при лёгкой нагрузке, но при серьёзной нагрузке они могут начать выкидывать NullPointerException или ConcurrentModificationException.
Кроме того всегда существует возможность “классической” синхронизации с помощью блока synchronized.
В заключение приведем общую диаграмму рассмотренной иерархии: