Форум: Форум PHPФорум ApacheФорум Регулярные ВыраженияФорум MySQLHTML+CSS+JavaScriptФорум FlashРазное
Новые темы: 0000000
PHP на примерах (2 издание). Авторы: Кузнецов М.В., Симдянов И.В. PHP 5. На примерах. Авторы: Кузнецов М.В., Симдянов И.В., Голышев С.В. MySQL на примерах. Авторы: Кузнецов М.В., Симдянов И.В. PHP Puzzles. Авторы: Кузнецов М.В., Симдянов И.В. Объектно-ориентированное программирование на PHP. Авторы: Кузнецов М.В., Симдянов И.В.
ВСЕ НАШИ КНИГИ
Консультационный центр SoftTime

Форум PHP

Выбрать другой форум

 

Здравствуйте, Посетитель!

вид форума:
Линейный форум Структурный форум

тема: Оцените мои попытки по использованию ООП
 
 автор: newProgrammer   (29.03.2009 в 22:05)   письмо автору
 
 

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

Имеет ли такой класс право на жизнь? Часто ли в реальных условиях случается так, что нужно несколько разных соединенний к БД? Вообще, бывают ли такие случаи?
Что сделал правильно, а что неправильно? Подскажите, пожалуйста.
Заранее большое спасибо.

<?php
class MySQL {
    
    
/**
     * Contains all instances of the MySQL class
     * 
     * @staticvar array
     */
    
private static $instances = array();
    
    
/**
     * Specify the connection parameters
     * NOTE: This is an associative array so the indexes are already specfied as:
     * - 'hostname';
     * - 'username';
     * - 'password';
     * Make sure you pass all the required parameters using the predifined indexes
     * 
     * @var array
     */
    
private $config = array(
        
'hostname' => '',
        
'username' => '',
        
'password' => '' 
    
);
    
    
/**
     * The Resource ID of the current connection
     * 
     * @var resource
     */
    
private $connection;
    
    
/**
     * The constructor method is private which prevents from direct initialization of an instance
     * 
     * @param array $config
     */
    
private function __construct($config) {
        
$this->config $config;
    }
    
    
/**
     * The getInstance() method used for setting an instance of MySQL class
     * 
     * It checks whether MySQL::$instances array is empty or has any previously set instances in it.
     * If no instance was set previously, it initiates new instance and pushes it to MySQL::$instances 
     * array. Otherwise, it checks if the connection parameters of the instance being initiated match 
     * the connection parameters of some other instance in MySQL::$instances array. If this is the case 
     * it returns that instance without initiating the new one with the same connection parameters.
     * If not, it initiates new instance and pushes it to the MySQL::$instances array.
     * 
     * @param array $config
     * @return MySQL instance
     */
    
public static function getInstance($config) {
        
# if there was no instance set previously, initiate the new one and push it to the array
        
if (empty(self::$instances)) {
            
$newInstance = new MySQL($config);
            
self::$instances[] = $newInstance;
            return 
$newInstance;
        
# otherwise check for a match
        
} else {
            foreach (
self::$instances as $instance) {
                if (
$instance->config == $config) {
                    return 
$instance;
                
# if no match found initiate the new one and push it to the array
                
} else {
                    
$newInstance = new MySQL($config);
                    
self::$instances[] = $newInstance;
                    return 
$newInstance;
                }
            }
        }
    }
    
    
/**
     * The open() method creates a connection to Database
     * 
     * @return resource $this->connection ID
     */
    
public function open() {
        
        
$this->connection mysql_connect(
            
$this->config['hostname'],
            
$this->config['username'],
            
$this->config['password']
        );
        
        if (!
$this->connection) {
            throw new 
MySQLExceptionmysql_error(),
                
'An error occurred while connecting to Database'
            
);
        }
        
        
mysql_query("SET NAMES 'cp1251'");
        return 
$this->connection;
    }
    
    
/**
     * The opened() method checks if the connection was properly created
     * 
     * @return boolean
     */
    
public function opened() { 
        if (
is_resource($this->connection)) { 
            return 
TRUE
        } else { 
            return 
FALSE
        } 
    }
    
    public function 
getMySQLInstances() {
        
print_r(self::$instances);
    }
    
    
/**
     * The close() method closes connection of the current instance
     * Nullifies the connection ID and unsets the instance from MySQL::$instances array
     */
    
public function close() { 
        
mysql_close($this->connection); 
        
$this->connection NULL;
        foreach (
self::$instances as $index => $instance) {
            if (
$instance->config == $this->config) {
                unset(
self::$instances[$index]);
            }
        }
    }
}
?>


Проверить в действии можно так:
<?php
$connection 
MySQL::getInstance(array(
    
'hostname' => 'localhost',
    
'username' => 'root',
    
'password' => ''
));

$connection->open();

if (
$connection->opened()) {
    echo 
'<pre>';
    
$connection->getMySQLInstances();
    echo 
'</pre>';
}

$connection->close();

echo 
'<pre>';
$connection->getMySQLInstances();
echo 
'</pre>';



$connection2 MySQL::getInstance(array(
    
'hostname' => 'localhost',
    
'username' => 'root',
    
'password' => ''
));

$connection2->open();

if (
$connection2->opened()) {
    echo 
'<pre>';
    
$connection2->getMySQLInstances();
    echo 
'</pre>';
}



$connection3 MySQL::getInstance(array(
    
'hostname' => '127.0.0.1',
    
'username' => 'root',
    
'password' => ''
));

$connection3->open();

if (
$connection3->opened()) {
    echo 
'<pre>';
    
$connection3->getMySQLInstances();
    echo 
'</pre>';
}
?>

  Ответить  
 
 автор: Mefisto84   (30.03.2009 в 04:33)   письмо автору
 
   для: newProgrammer   (29.03.2009 в 22:05)
 

Сделал сам? :-) Вот эти строчки заставляют усомниться, или ты всегда пишешь комменты к своих скриптах на английском? :-))

The getInstance() method used for setting an instance of MySQL class 
     *  
     * It checks whether MySQL::$instances array is empty or has any previously set instances in it. 
     * If no instance was set previously, it initiates new instance and pushes it to MySQL::$instances  
     * array. Otherwise, it checks if the connection parameters of the instance being initiated match  
     * the connection parameters of some other instance in MySQL::$instances array. If this is the case  
     * it returns that instance without initiating the new one with the same connection parameters. 
     * If not, it initiates new instance and pushes it to the MySQL::$instances array. 
     *  

  Ответить  
 
 автор: newProgrammer   (30.03.2009 в 14:33)   письмо автору
 
   для: Mefisto84   (30.03.2009 в 04:33)
 

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

PS Только, пожалуйста, давайте по теме, для меня PHP важнее, чем английский :))
PPS Если что переведу... :)

  Ответить  
 
 автор: Axxil   (30.03.2009 в 15:48)   письмо автору
 
   для: newProgrammer   (29.03.2009 в 22:05)
 

Шаблон синглетон изучаем?

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

Такие правильные, вроде, но ненужные классы очень скучно разбирать.

Попробуйте писать вещи, которые сами будете на 100% использовать. Тогда и обсуждение и разбор будут гораздо информативнее и полезнее.

  Ответить  
 
 автор: newProgrammer   (30.03.2009 в 18:42)   письмо автору
 
   для: Axxil   (30.03.2009 в 15:48)
 

Спасибо, Axxil.

Это я и хотел узнать. Значит несколько соединений в рамках одного скрипта используются редко. Теперь я понимаю, что в ближайшее время мне-то уж точно такой класс не пригодится.

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

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

  Ответить  
 
 автор: mihdan   (11.12.2009 в 18:04)   письмо автору
 
   для: Axxil   (30.03.2009 в 15:48)
 

В проеутах своих почти постоянно работаю одновременно с четырьмя базами - это не странно

  Ответить  
 
 автор: Fractured#   (11.12.2009 в 18:17)   письмо автору
 
   для: mihdan   (11.12.2009 в 18:04)
 

Это сверхпрофессионализм — работать сразу с 4-мя БД. Вероятно, проект больно хорошо устроен. лол)

  Ответить  
 
 автор: mihdan   (12.12.2009 в 13:16)   письмо автору
 
   для: Fractured#   (11.12.2009 в 18:17)
 

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

  Ответить  
 
 автор: DEM   (12.12.2009 в 13:26)   письмо автору
 
   для: Fractured#   (11.12.2009 в 18:17)
 

Банальный пример: браузерные игры с чатом.

Чат почти всегда будет находится в отдельнйо базе (конечно я говорю про более-менее развитую игру, а не игру в которую играют одновремено всего 100 человек)

  Ответить  
 
 автор: Trianon   (12.12.2009 в 13:48)   письмо автору
 
   для: newProgrammer   (29.03.2009 в 22:05)
 

Всё так чистенько, аккуратненько, бесполезненько, и вдруг, как обухом по башке
mysql_query("SET NAMES 'cp1251'"); 

Ы...

  Ответить  
 
 автор: slo_nik   (12.12.2009 в 15:16)   письмо автору
 
   для: Trianon   (12.12.2009 в 13:48)
 

а что в этой строке не так?

  Ответить  
 
 автор: Valick   (12.12.2009 в 15:22)   письмо автору
 
   для: slo_nik   (12.12.2009 в 15:16)
 

присутствие

  Ответить  
 
 автор: Trianon   (12.12.2009 в 15:31)   письмо автору
 
   для: slo_nik   (12.12.2009 в 15:16)
 

Откуда класс знает, какая у меня кодировка на сайте?

  Ответить  
 
 автор: Slo_Nik   (12.12.2009 в 15:40)   письмо автору
 
   для: Trianon   (12.12.2009 в 15:31)
 

да, действительно...
получается, что в классе надо задавать кодировку?

  Ответить  
 
 автор: Николай2357   (12.12.2009 в 15:59)   письмо автору
 
   для: Slo_Nik   (12.12.2009 в 15:40)
 

Мне всегда любопытно...
А для чего вообще столько индусского кода возни? Ведь это все решается тремя строчкми. Вот сейчас еще пару методов добавится - кодировку устанавливать...

  Ответить  
 
 автор: cheops   (12.12.2009 в 16:18)   письмо автору
 
   для: Николай2357   (12.12.2009 в 15:59)
 

Обертка для MySQL-функций может быть полезна:
1. Для безболезненного перехода на другую базу данных
2. Для генерации исключений и логгирования ошибок. Ошибки SQL-запосов никак не фигурируют в среде PHP, поэтому их обработка всегда лежит на плечах программиста. Чтобы этот пласт автоматизировать по любому придется писать обертку или в виде собственного набора фукнций или в виде класса.

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

  Ответить  
 
 автор: Николай2357   (12.12.2009 в 16:58)   письмо автору
 
   для: cheops   (12.12.2009 в 16:18)
 

Обертка для MySQL-функций может быть полезна:
Я знаю для чего делается обертка для mysql_query() . Для диагностики ошибок очень удобно.
Я интересуюсь другим, а именно организацией соединения
Безболезненный переход на другую бд - аргумент притянутый за уши. Потому что
1. Это происходит крайне редко.
2. Это решается проще и эфективнее - сменой файла коннекта.
3. А вот то, что сей код будет неоправданно тормозить и кушать ресурс - очевидно.

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

  Ответить  
 
 автор: Trianon   (12.12.2009 в 17:17)   письмо автору
 
   для: Николай2357   (12.12.2009 в 16:58)
 

На этот случай лучше ставить стакан и горшок.

  Ответить  
 
 автор: Саня   (12.12.2009 в 22:06)   письмо автору
 
   для: Николай2357   (12.12.2009 в 16:58)
 

Я тут давеча познакомился с альтернативным интерпретатором PHP — quercus. Ох и мощная штука. Со встроенной поддержкой юникода. Впечатлился настолько, что решил подогнать под него текущий, разрабаываемый мной, проект (на ZF, кстати говоря) и выложить на google app engine. Готовлю статью на эту тему.

  Ответить  
 
 автор: cheops   (12.12.2009 в 16:20)   письмо автору
 
   для: Slo_Nik   (12.12.2009 в 15:40)
 

>да, действительно...
>получается, что в классе надо задавать кодировку?
Хорошо бы предусмотреть такую необязательную возможность. Возможно, вы потом сами перейдете на UTF-8 и класс должен предоставлять такую возможность. Хорошо также если бы он по умолчанию использовал cp1251 с которой вы вероятно хотите иметь дело большую часть времени.

  Ответить  
 
 автор: Trianon   (12.12.2009 в 16:29)   письмо автору
 
   для: cheops   (12.12.2009 в 16:20)
 

Вероятно, хотеть иметь дело большую часть времени следует именно с utf-8. Нет?
Я понимаю, что личные желания - дело тонкое... но надо же что-то делать, Аркадий! работать над собой!

  Ответить  
 
 автор: cheops   (12.12.2009 в 16:40)   письмо автору
 
   для: Trianon   (12.12.2009 в 16:29)
 

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

  Ответить  
 
 автор: Trianon   (12.12.2009 в 16:44)   письмо автору
 
   для: cheops   (12.12.2009 в 16:40)
 

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

  Ответить  
 
 автор: cheops   (12.12.2009 в 16:50)   письмо автору
 
   для: Trianon   (12.12.2009 в 16:44)
 

Скорее всего повсеместный переход на UTF-8 продлится ещё несколько лет...
Достоинства UTF-8 можно перечислять очень долго, это и безболезненный многоязыковой сайт и беззаморочный AJAX. Однако имеются и недостатки, которые подзатормаживают такой переход: чуть потяжелее однобайтовой кодировки, отстутствие поддержки на уровне ядра PHP (хотя в ядре строковые функции такие разношерстные, что и плевать) и отсуствие регистронезависимого сопоставления в MySQL.

  Ответить  
 
 автор: Trianon   (12.12.2009 в 16:55)   письмо автору
 
   для: cheops   (12.12.2009 в 16:50)
 

>отсуствие регистронезависимого сопоставления в MySQL.

Точно отсутствует?

  Ответить  
 
 автор: cheops   (12.12.2009 в 23:35)   письмо автору
 
   для: Trianon   (12.12.2009 в 16:55)
 

Собственно глубоко не копал, но пошарив вокруг, что-то не нащупал готового решения (вот так чтобы был готовый _ci без гвоздей). Если у вас есть готовое решение или направление, куда копать поделитесь, плиз?

  Ответить  
 
 автор: Trianon   (13.12.2009 в 00:00)   письмо автору
 
   для: cheops   (12.12.2009 в 23:35)
 

Я тоже копал а) давно и б) неглубоко.
Но вроде как, из того что помню, наличие/отсутствие подходящих сопоставлений UTF-8 определяется полнотой установки сервера SQL (вроде соответствующие xml-файлы описывают сопоставления)
Так что и _cs и _ci достижимы.

Более точно http://dev.mysql.com/doc/refman/5.0/en/adding-collation-unicode-uca.html

  Ответить  
 
 автор: cheops   (13.12.2009 в 12:15)   письмо автору
 
   для: Trianon   (13.12.2009 в 00:00)
 

Хм... любопытно с 5.0.45 даже без перекомпиляции добавить можно... только я так понимаю по ссылке предлагается кодировку для своих нужд самому создать (т.е. скажем русский вариант utf8_russian_ci)... Это бы ещё и хостера уговорить создать такую кодировку. Хм... однако для своих серверов и для одного-двух языков - это пожалуй выход.

  Ответить  
 
 автор: Trianon   (13.12.2009 в 12:42)   письмо автору
 
   для: cheops   (13.12.2009 в 12:15)
 

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

  Ответить  
 
 автор: Slo_Nik   (12.12.2009 в 16:58)   письмо автору
 
   для: cheops   (12.12.2009 в 16:20)
 

да вот уже припёрло перейти на utf-8, как раз из - за попытки внедрить ajax :):):):)

  Ответить  
 
 автор: cheops   (12.12.2009 в 23:36)   письмо автору
 
   для: Slo_Nik   (12.12.2009 в 16:58)
 

Переходить лучше раньше, чем позже, особенно, если коммерческим кодом обрасти не успели :)))

  Ответить  
 
 автор: Slo_Nik   (13.12.2009 в 07:34)   письмо автору
 
   для: cheops   (12.12.2009 в 23:36)
 

>коммерческим кодом обрасти не успели

что Вы имели ввиду?

  Ответить  
 
 автор: cheops   (13.12.2009 в 12:11)   письмо автору
 
   для: Slo_Nik   (13.12.2009 в 07:34)
 

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

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

  Ответить  
 
 автор: Slo_Nik   (13.12.2009 в 13:08)   письмо автору
 
   для: cheops   (13.12.2009 в 12:11)
 

спасибо за разъяснения.

  Ответить  
Rambler's Top100
вверх

Rambler's Top100 Яндекс.Метрика Яндекс цитирования