Так после скролла наверх эта же кнопка меняет иконку на «Вниз» и функционирует как «ну пожалуйста, верните меня обратно в середину страницы». Разве нет?
Это чтобы добраться до Земли. Он мог писать сюда, используя радиоволны. С другой стороны, им тоже требуется минимум 1 час 15 минут в один конец, так что он точно не с Энцелада.
Насчет поразмыслить — это само собой разумеется. Если библиотека предоставляет что-либо, позволяющее контролировать процесс на протяжении всей его длительности, то проблемы нет вообще. Но, к сожалению, реальная ситуация от этого зачастую далека.
Все-таки, как мне кажется, лучше отталкиваться от того, что система в большинстве случаев отработает правильно и в разумные для объема данных сроки. И прогрессбар, минуту висящий на 5% (или 95%, по вкусу) не добавит спокойствия пользователю, это немногим лучше, чем вообще отсутствие прогрессбара, как такового. Будут мысли о том, что программа зависла, что произошла какая-то ошибка и это томительное ожидание никогда не закончится.
Такая реализация не отражает реального процента загрузки, и соответственно, ничем не лучше циклического прогрессбара.
Тут ниже уже высказывалась точка зрения, что такая реализация даже наоборот, запутывает: человек видит, что прошло 95% и уверен, что ждать осталось считанные секунды. А секунды идут и идут, плавно перетекая в минуты.
Собственно, поиск в упомянутой семерке по достаточно большому количеству неиндексированных файлов в подобную ситуацию и выливается: совершенно непонятно, сколько еще осталось ждать.
PS. Кстати говоря, по этой причине реализация поиска в семерке лично меня, например, подсознательно отталкивает.
Процесс может и идти. Представим некую библиотеку, которая сохраняет данные, ну, скажем, в формате таблицы Excel. И у нее, очевидно, есть некий метод save. И этот метод — практически единственное, что есть в обработчике кнопки «Сохранить» в вашем приложении.
Каким образом узнать, сколько процентов данных на данный момент сохранено? Без вмешательства в исходный код библиотеки, естественно.
Шагов не всегда достаточное количество. Разработчик не всегда имеет возможность отследить состояние выполнения процесса, если, например, речь идет о вызове функции из сторонней библиотеки или фреймворка.
Кстати, да. При открытии вкладки фоном (например, через клик средней кнопкой мыши или Ctrl+кликом) в последнем Firefox карта банально не загружается. Хотя в Chrome, например, такого бага нет.
Интересный эффект наблюдается, если открыть эту вкладку, как единственную, при условии, что в настройках установлено восстанавливать вкладки, которые были открыты при закрытии браузера (либо если этот сайт установлен домашней страницей). Браузер закрывается сразу после запуска и, если в случае с восстановлением последних закрытых вкладок достаточно успеть нажать Ctrl+T, то при установке домашней страницей без правки конфигов или файла hosts не обойтись.
Проверено в Firefox 22.0 и в Google Chrome.
Да, я скорее имел в виду контроллер. К сожалению, путаюсь в терминологии.
В данном случае, как я уже сказал, менять не нужно вообще ничего при условии, что названия свойств остаются теми же. В этой статье я лишь немного коснулся темы адаптеров, но вообще они позволяют легко и просто переключаться между работой с разнообразными хранилищами, будь то база данных, реляционная или нет, файлы, что угодно. Главное, чтобы оттуда можно было прочитать данные, туда можно было записать данные и оттуда можно было удалить данные.
Вопрос, как мне кажется, только в том, какая часть логики хранится в модели и хранится ли вообще. Если чутко чувствовать и соблюдать эту грань, то даже при наличии определенного количества логики в моделях, можно избежать и сложноподдерживаемого кода и трудноуловимых ошибок. При этом, это в определенной мере позволит избавиться от дублирования кода в случае с разного рода валидацией данных.
При смене одной ORM на другую в любом случае придется переделывать бизнес-логику, либо нужно делать доступ к данным «точно такой же, как в %ORM-name%». Если вы имеете в виду, к примеру, переход с MySQL на PostgreSQL, то на этот случай предусмотрены адаптеры подключения к БД и переход в данном случае проходит вполне безболезненно, заменяя лишь класс, от которого наследуется модель.
Кодогенерация — это один из выходов. Другой выход — это как раз использование магии. Оба подхода имеют свои плюсы и минусы. Плюс магического, в частности, в том, что не нет строгого набора данных.
Вот пример: есть, допустим, стороннее API и есть модель, которая с ним работает. API обновилось, добавилось новое свойство. Его можно использовать сразу же, не редактируя модель. Это полезно, когда разработкой фреймворка занимается один человек, а написанием бизнес-логики — другой.
Никто не спорит, что использование __call медленнее, а дополнительные системы вроде ORM тоже дают определенную нагрузку. Но на другой чаше весов скорость написания кода, удобство его поддержки и чисто субъективная понятность. Грубо говоря, можно все это написать на ассемблере, и это будет определенно быстрее обычных вызовов.
Хороший программист должен думать обо всем, но не все являются хорошими программистами. Зачастую лучше предоставить вот такую «автоматическую коробку передач», которая позволяет добраться из точки А в точку Б не требуя от программиста погружаться в дебри реализации. лично мне спокойнее на душе, когда я знаю, что мой коллега ничего не забудет, потому что я это уже предусмотрел в самой модели. Но я, разумеется, понимаю, что это нарушение заповеди «не храни логику в модели» :)
Если честно, не совсем понял логику. Вы имеете в виду, что должен быть некий централизованный объект, который умеет сохранять любую запись в базу? А если мне при сохранении именно товаров нужно сделать еще что-то, в лог запись добавить, например?
По поводу усложнения чтения кода я не соглашусь, потому что, на мой взгляд, куча проверок перед изменением записи (если использовать запись «сырых» данных, используя, например, $instance->price = 12.95) нисколько не облегчает чтение кода, и, кроме того, зачастую приводит к его дублированию. А если использовать генерируемые методы, то внешне (в логике приложения) это не будет отличаться от данного подхода ничем, кроме этих самых двух регулярок, которые, при наличии дополнительной логики при установке значения, не используются.
Этот механизм не претендует на то, чтобы заткнуть за пояс известные ORM. Это просто иллюстрация еще одного подхода, который, на мой взгляд ии по моему опыту, достаточно удобен в использовании.
Да, определенные проблемы с производительностью могут иметь место. По большому счету, для этого есть прямой set() без регулярок. Если нужна дополнительная логика, то можно переопределить тот же метод setDescription() в самой модели, вызывая в конце set('description', $value) или parent::setDescription(). Но в целом, да, вы правы, здесь производительность жертвуется в угоду удобочитабельности и наглядности.
По поводу ошибок в данных я лично представляю себе только вариант с исключениями, руководствуясь тем, что если произошла критическая ошибка, то программа должна остановиться, выбросить исключение и «спросить» у программиста, что же делать в подобной ситуации. Для этого я создам три десятка исключений на каждую модель, наследующихся друг от друга, и в try… catch… catch… catch буду указывать, что нужно делать в подобной ситуации. Для некритических ошибок подошел бы вариант с неким подобием предупреждений (warnings), но на эту тему я пока, к сожалению, не думал.
Все-таки, как мне кажется, лучше отталкиваться от того, что система в большинстве случаев отработает правильно и в разумные для объема данных сроки. И прогрессбар, минуту висящий на 5% (или 95%, по вкусу) не добавит спокойствия пользователю, это немногим лучше, чем вообще отсутствие прогрессбара, как такового. Будут мысли о том, что программа зависла, что произошла какая-то ошибка и это томительное ожидание никогда не закончится.
Тут ниже уже высказывалась точка зрения, что такая реализация даже наоборот, запутывает: человек видит, что прошло 95% и уверен, что ждать осталось считанные секунды. А секунды идут и идут, плавно перетекая в минуты.
Собственно, поиск в упомянутой семерке по достаточно большому количеству неиндексированных файлов в подобную ситуацию и выливается: совершенно непонятно, сколько еще осталось ждать.
PS. Кстати говоря, по этой причине реализация поиска в семерке лично меня, например, подсознательно отталкивает.
Каким образом узнать, сколько процентов данных на данный момент сохранено? Без вмешательства в исходный код библиотеки, естественно.
Проверено в Firefox 22.0 и в Google Chrome.
В данном случае, как я уже сказал, менять не нужно вообще ничего при условии, что названия свойств остаются теми же. В этой статье я лишь немного коснулся темы адаптеров, но вообще они позволяют легко и просто переключаться между работой с разнообразными хранилищами, будь то база данных, реляционная или нет, файлы, что угодно. Главное, чтобы оттуда можно было прочитать данные, туда можно было записать данные и оттуда можно было удалить данные.
При смене одной ORM на другую в любом случае придется переделывать бизнес-логику, либо нужно делать доступ к данным «точно такой же, как в %ORM-name%». Если вы имеете в виду, к примеру, переход с MySQL на PostgreSQL, то на этот случай предусмотрены адаптеры подключения к БД и переход в данном случае проходит вполне безболезненно, заменяя лишь класс, от которого наследуется модель.
Вот пример: есть, допустим, стороннее API и есть модель, которая с ним работает. API обновилось, добавилось новое свойство. Его можно использовать сразу же, не редактируя модель. Это полезно, когда разработкой фреймворка занимается один человек, а написанием бизнес-логики — другой.
Хороший программист должен думать обо всем, но не все являются хорошими программистами. Зачастую лучше предоставить вот такую «автоматическую коробку передач», которая позволяет добраться из точки А в точку Б не требуя от программиста погружаться в дебри реализации. лично мне спокойнее на душе, когда я знаю, что мой коллега ничего не забудет, потому что я это уже предусмотрел в самой модели. Но я, разумеется, понимаю, что это нарушение заповеди «не храни логику в модели» :)
Этот механизм не претендует на то, чтобы заткнуть за пояс известные ORM. Это просто иллюстрация еще одного подхода, который, на мой взгляд ии по моему опыту, достаточно удобен в использовании.
Да, определенные проблемы с производительностью могут иметь место. По большому счету, для этого есть прямой set() без регулярок. Если нужна дополнительная логика, то можно переопределить тот же метод setDescription() в самой модели, вызывая в конце set('description', $value) или parent::setDescription(). Но в целом, да, вы правы, здесь производительность жертвуется в угоду удобочитабельности и наглядности.
По поводу ошибок в данных я лично представляю себе только вариант с исключениями, руководствуясь тем, что если произошла критическая ошибка, то программа должна остановиться, выбросить исключение и «спросить» у программиста, что же делать в подобной ситуации. Для этого я создам три десятка исключений на каждую модель, наследующихся друг от друга, и в try… catch… catch… catch буду указывать, что нужно делать в подобной ситуации. Для некритических ошибок подошел бы вариант с неким подобием предупреждений (warnings), но на эту тему я пока, к сожалению, не думал.