Форум Flasher.ru
Ближайшие курсы в Школе RealTime
Список интенсивных курсов: [см.]  
  
Специальные предложения: [см.]  
  
 
Блоги Правила Справка Пользователи Календарь Поиск рулит! Сообщения за день Все разделы прочитаны
 

Вернуться   Форум Flasher.ru > Блоги > Идиотизмы

Даже в определениях идиотизма встречается идиотизм.
Цитата:
Идиотизм — устаревшее название идиомы
Идиома в программировании — понятие близкое к понятию шаблона проектирования. Идиомы представляют собой шаблоны проектирования, учитывающие специфику конкретного языка программирования и потому не универсальные. Это хорошие решения проектирования для конкретного языка или программной платформы.
Рейтинг: 5.00. Голосов: 2.

Идиотизмы: Socket

Запись от BlooDHounD размещена 23.04.2010 в 14:34
Обновил(-а) BlooDHounD 07.06.2010 в 17:11

для понимания материала необходимы следующие знания:
flash.net.Socket
Подключение к сокетам




ну вот за что флэшерам такие мучения? Socket, казалось, ну что можно сломать в таком примитивном классе? анннет.
и так.
1. мы пытаемся законектися.
2. допустим наш сервер лежит.
3. нам само сабой вываливается ioError.
4. мы, узнав о такой трагедии, расстраиваемся и отписываемся от всех событий.
5. получаем unhadled securityError, так как policy-file нам тоже не удалось получить.

замечательно! вот только с откуда я могу знать, что после ioError я 100% получу securityError? а если у меня на 843 порту ещё один демон болтается? мне на всегда события оставлять висеть? до здравствуют утечки?

исправленный класс Socket:
Код AS3:
package blooddy.patch.net {
 
	import flash.events.ErrorEvent;
	import flash.events.Event;
	import flash.events.IOErrorEvent;
	import flash.events.SecurityErrorEvent;
	import flash.net.Socket;
 
	/**
	 * @author					BlooDHounD
	 * @version					1.0
	 * @playerversion			Flash 9
	 * @langversion				3.0
	 */
	public class Socket extends flash.net.Socket {
 
		//--------------------------------------------------------------------------
		//
		//  Constructor
		//
		//--------------------------------------------------------------------------
 
		/**
		 * @inheritDoc
		 */
		public function Socket(host:String=null, port:int=0.0) {
			super( host, port );
			super.addEventListener( Event.CLOSE,						this.handler_close, false, int.MAX_VALUE, true );
			super.addEventListener( IOErrorEvent.IO_ERROR,				this.handler_error, false, int.MAX_VALUE, true );
			super.addEventListener( SecurityErrorEvent.SECURITY_ERROR,	this.handler_error, false, int.MAX_VALUE, true );
		}
 
		//--------------------------------------------------------------------------
		//
		//  Variables
		//
		//--------------------------------------------------------------------------
 
		/**
		 * @private
		 */
		private var _hasError:Boolean = false;
 
		//--------------------------------------------------------------------------
		//
		//  Overrided methods: Socket
		//
		//--------------------------------------------------------------------------
 
		/**
		 * @inheritDoc
		 */
		public override function connect(host:String, port:int):void {
			super.connect( host, port );
			this._hasError = false;
		}
 
		/**
		 * @inheritDoc
		 */
		public override function close():void {
			super.close();
			this._hasError = true;
		}
 
		//--------------------------------------------------------------------------
		//
		//  Event handlers
		//
		//--------------------------------------------------------------------------
 
		/**
		 * @private
		 */
		private function handler_close(event:Event):void {
			this._hasError = true;
		}
 
		/**
		 * @private
		 */
		private function handler_error(event:ErrorEvent):void {
			if ( this._hasError ) {
				// ошибка уже была. поэтому блокируем остальные
				event.stopImmediatePropagation();
			} else {
				this._hasError = true;
				// надо оптисаться, что бы не мешать вызову исключения
				super.removeEventListener( event.type, this.handler_error );
				if ( !super.hasEventListener( event.type ) ) {
					// если подписчиков нету, диспатчим ошибку, что бы вывалился unhadled securityError
					super.dispatchEvent( event );
				}
				// подписываемся обратно
				super.addEventListener( event.type, this.handler_error, false, int.MAX_VALUE, true );
			}
		}
 
	}
 
}
Всего комментариев 60

Комментарии

Старый 14.04.2011 08:49 alexcon314 вне форума
alexcon314
Цитата:
проводник при этом занял 0.1% от времени ЦПЮ, а флеш - 30%
А я упрямый. Нет. Специально повторил. Соотношение где-то 1:2 (1-2% vs 2-4%) в пользу проводника. С учетом паковки/распаковки данных и пр. о чем я упомянул, ну, и само-собой рантаймовских ликов - нормально. Не сомневаюсь, что если чего-то там еще соптимизировать, то и здесь разница станет несущественной.
Цитата:
когда ЦПЮ работает в режиме сервера для компиляции - тогда числа будут совсем другими... Т.е. у нас есть ограничение по времени не связаное с рантаймом, предположим, пропускная способность шины, или записи на диск - они в любом случае медленнее обращений к памяти / ЦПЮ, поэтому, в "обычном" режиме мы, возможно, ничего и не заметим.
Можно, конешно, бомбочку ядерную под "ЦПЮ в режиме сервера для компиляции" подложить еще, тогда ваще атас.. флеш точно зависнет. Навсегда.. Неясно только, нафик его там вообще запускать, или он имеет какое-то отношение к организации/реализации высоконагруженных сервисов? Да здравствует обычный режим!
ЗЫ Еще раз пардон за офтоп.
И да, кажись я понял Олега.
Ему хочется такую "фиковину" в языке АС (я, конечно, утрирую):
- которая типа ByteArray с его write/read методами, но не ByteArray, ибо он сильно ресурсы жрет.
- которая заточена на работу с файлами/сокетами нативно. т.е. там write/read будут при исполнении в рантайме дергать очень быстро очень быстрые нативные фичи, и если это возможно, хотелось бы иметь доступ не просто к фичам, но в kernel mode при нужде (а она несомненно будет) вываливаться.
- которая будет заточена под работу с огромными (а лучше с очень огромными) объемами данных.
- вот.
Обновил(-а) alexcon314 14.04.2011 в 10:49
Старый 14.04.2011 13:56 wvxvw вне форума
wvxvw
 
Аватар для wvxvw
Да, а на картинке - там фотошоп наверное, и я специально вас обманываю. Не знаю, может в Виндовсе быстрее, я не пробовал.

Почему нужно: приложение, даже не очень большое хочется тестировать автоматически, тестировать только одну копию приложения - это совсем непродуктивно, хотелось бы, ну, хотя бы с десяток с разными настройками и т.п. И тут оказалось, что логи из флеша вывести безумно накладно. Но вывести - это еще полбеды, а вот передать ему информацию во время теста - напряг, а если при этом флеш должен не просто картинку показывать, а еще и делать что-то... Сервер, который будет тестировать приложение - это совсем другой мир очень мало похожий на ПК разработчика, можно сравнить с солнечной системой Если на ПК ситуация когда все ядра процессора заняты на 100% - исключение, то на таком сервере она всегда такая, так же как на поверхности земли температуры выше 50 градусов случаются достаточно редко, и вам не нужны скафандры, чтобы ходить по улице, а вот ближе к солнцу будет немного теплее...
Еще одна причина запустить много процессов флеша на одной машине - тривиальное логирование деятельности, предположим флеш проигрывает видео или аудио и вам хочется его какими-то автоматическими инструментами обрабатывать. (В моей конкретной ситуации это связано с тем, что, пользователи приложения иногда нарушают dressing codes - а именно позируют перед камерой в неглиже, а то и без неглиже и хотелось бы такие ситуации отлавливать. (кроме нудистов есть еще много параметров, которые хотелось бы отфильтровать). Когда пользователей в общем около миллиона, то одной запущеной копии приложения для логирования очевидно будет недостаточно, хотелось бы, как минимум, несколько десятков... Так что причины не высосаны из пальца.

Но суть моего изначального поста была совсем не в этом, а в том, что благодаря дурацкому дизайну, буфер при копировании нужно создавать во флеше, хотя были все предпосылки для того, чтобы это сделать на нативном уровне. Т.е. я не вижу никакой причины, которая могла бы помешать всему, что является IDataOutput иметь метод writeBytes(bytes:IDataOutput, ....). ByteArray, как тип первого аргумента в этой функции - это случайность, кроме того, она мешает расширяемости.
Старый 14.04.2011 16:04 alexcon314 вне форума
alexcon314
Вот. Отлично.
Мое резюме:
- у сокета/файлстрима есть нативный буфер который рефлектится в ас как ByteArray, рантайм обрабатывает этот буфер нативно же (ну, как может). Хочешь ты или нет, надо оно тебе или нет, ты работаешь в итоге только с ним, не с чем там больше работать.
- твои IDataInput/IDataOutput - будет не что иное, как обертка над этим нативным буфером, т.е. дополнительные тормоза (все эти стейты, метаданные и прочий мусор, да?). См. так же п.1.
- расширять тут нехрен и незачем, интерфейс имплеменить - ради бога. Впрочем, не настаиваю.
- операцию копирования данных напрямую из одного буфера в другой невозможно сделать управляемой (прозрачной) при асинхронности потоков чтения/записи без промежуточного буфера и вот он не может быть нативным никак.
- синхронные потоки = еще большие тормоза.
- твой облом с выгрузкой логов - это, видимо, судьба. попробуй дампить логи из памяти без флеша, еслу уж невпротык.
Обновил(-а) alexcon314 14.04.2011 в 16:15
Старый 14.04.2011 23:55 wvxvw вне форума
wvxvw
 
Аватар для wvxvw
Какая обертка? Интерфейс это не обертка, это набор правил, которым следует какой-то объект. ByteArray ужЕ имплементит этот интерфейс - это что, как-то сказывается на вызовах readByte? На производительности сказывается то, что каждый вызов readByte флеш должен записать, проверить когда он случился, записать состояние до того как случился и т.д. А от того, что этот метод описан в интерфейсе ничего не меняется во время выполнения.
ByteArray - это такая же надстройка над системными утилитами, как и сокеты и потоки (флешевые), нет абсолютно никаких оснований выделять его в отдельную категорию, когда речь идет о возможности записать Х байт - сокеты и стримы могут это делать точно так же, просто интерфейс, т.е. набор правил задан так, что нельзя абстрагироваться от того, куда конкретно делается запись. Более того, в исключительных ситуациях, таких как была описана выше, этот подход оказывается еще и очень затратным.
> расширять тут нехрен и незачем, интерфейс имплеменить - ради бога. Впрочем, не настаиваю.
Я не хочу имплементить интерфейс, мне нужно, чтобы его по-другому имплементили сокет и потоки.

> операцию копирования данных напрямую из одного буфера в другой невозможно сделать управляемой (прозрачной) при асинхронности потоков чтения/записи без промежуточного буфера и вот он не может быть нативным никак.
Так мне именно что не нужна прозрачность, и буффер да, вполне может быть нативным. Я даже не хочу передавать байты, только позицию откуда читать и куда читать. Если проблема в том, что это "занимает много времени", так оно и сейчас занимает столько же времени при копировании в ByteArray - и от того, что появится возможность точно так же копировать в сокет или поток, ничего в смысле времени не поменяется. Да, если подумать, было бы здорово, если бы у сокета или массива байт были асинхронные методы для записи больших объемов информации, но это уже выходит за рамки обсуждения.

Дампить из памяти а потом догадываться, что 0x8023F456 было вызовом addChild()? Идея интересная, и я думаю, я узнаю много нового про устройство плеера и про то, как устроена память, JIT и ARM... но это немножко через чур для меня

Или, ок, давайте посмотрим на это по-другому. Что ухудшится, если writeBytes будет писАть во все, что является IDataOutput? Ведь у всего, что является IDataOutput есть метод writeBytes, значит, объекты такого типа потенциально могу записывать много байт одновременно. Приведите хотя бы один пример, когда эта ситуация может оказаться ошибочной или бессмысленной.
Старый 15.04.2011 00:06 BlooDHounD вне форума
BlooDHounD
 
Аватар для BlooDHounD
я уже устал тебе повторять. для начала упадёт производительность.
Старый 15.04.2011 01:55 wvxvw вне форума
wvxvw
 
Аватар для wvxvw
От чего она упадет? В классе ByteArray и его реализации не изменится НИ-ЧЕ-ГО вообще, ни один байт. Почему упадет производительность?
Вот у тебя есть 2 функции:
Код:
function foo(parameter:IBitmapDrawable):void { trace(parameter); }
function bar(parameter:BitmapData):void { trace(parameter); }
Что, какая-то из них более затратная / менее производительная, в каком месте?
Старый 15.04.2011 02:49 BlooDHounD вне форума
BlooDHounD
 
Аватар для BlooDHounD
олег. я устал. я ухожу ) извини, но это уже смешно.
Старый 15.04.2011 04:55 mayakwd вне форума
mayakwd
 
Аватар для mayakwd
я устал, я ухожуй.
Старый 15.04.2011 06:45 i.o. вне форума
i.o.
 
Аватар для i.o.
Илюха, флудильня в другом месте)
Старый 15.04.2011 06:47 mayakwd вне форума
mayakwd
 
Аватар для mayakwd
судя по комментам ты ошибаешься
 

 


Часовой пояс GMT +4, время: 18:42.


Copyright © 1999-2008 Flasher.ru. All rights reserved.
Работает на vBulletin®. Copyright ©2000 - 2024, Jelsoft Enterprises Ltd. Перевод: zCarot
Администрация сайта не несёт ответственности за любую предоставленную посетителями информацию. Подробнее см. Правила.