суббота, 29 декабря 2007 г.

Google Mail

Случайно обнаружил внизу страницы надпись:
You are currently using 197 MB (3%) of your 6111 MB.
А ведь год назад 2GB было! Растём...

пятница, 28 декабря 2007 г.

Масяня

Куваев выпустил очередную серию.
Ну почему он Бо не продолжает!!!

Чапаев

Помнится в дедстве играли...

среда, 26 декабря 2007 г.

Стихи

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

С Новым Годом!

В прошлую пятницу у нас был корпоративный праздник для детей. Поначалу Мишка на все серьёзно смотрел, анализировал. Снегурочке удалось его в хоровод завести, но он достаточно быстро отвалился. Ну не знает он как водить хоровод...

Вроде и в ладоши хлопал, но всё это с таким серьёзным выражением лица. Ждал Деда Мороза, так как много о нём наслышан. Любит получать от него подарки ;)
У него Дед Мороз - любимая мягкая игрушка.

По пути заехали за семьёй моего начальника (на Маршала Казакова). Протестировали съезд с КАД на Таллинское шоссе. В общем, теперь знаем, что до Пашки ехать 30-40 минут. Есть два узких места: две полосы на КАД от Рыбацкого до Московского и очень узкое Таллинское шоссе. Оттуда поехали по Стачек и на Старо-Петергофском встряли. Добрались до офиса за 15 минут до начала. Обратно ехали тем же маршрутом, но без пробок. Въезд на КАД с Таллинского шоссе только со стороны области. Пришлось разворачиваться.

Протестировали Ленту на Таллинском шоссе. Очень большой магазин! Легко можно заблудиться. Потратили час или два просто прицениться...
При выезде со стоянки на шоссе стояла группа гопников. Кинули петарду под колеса. Какой-то хмырь решил открыть дверцу, но... центральный замок рулит!
Короче, в 11 вечера уставшие, но довольные приехали домой.

понедельник, 24 декабря 2007 г.

Manowar

17-го декабря на официальном сайте группы появилось сообщение: Фаны давно просили нас придумать какие-нибудь товары с нашей маркой. Мы услышали эти просьбы и сделали презервативы MANOWAR. Теперь вы можете не только сказать Fuck The World, но и сделать это!
Интересно, на что они намекают? На глобус???

среда, 19 декабря 2007 г.

У Рудольфа II

Вчера с бывшим коллегой по Борланду сидели в этом ресторане. Он приехал на некоторое время из штатов, где сейчас драйвера пишет для Nvidia.
Заведение резко подорожало, несмотря на то, что порции уменьшились. Мы выпили по литру пива, топинки и вяленую свинину на двоих и по порции основного блюда. А заплатили 2000 р.
Обслуживание всё такое же медленное. Крушовицы - нет! Пришлось пить Килкенни. Скрипач теперь скрипит не один, а с женой. Она - на синтезаторе. На выходе взял журнальчик Гамбринус, который рекламирует чешские пивницы в Питере, а там на развороте тетка в одних трусах. И подпись: мисс ноябрь, официантка ресторана У Рудольфа II. Там же приведен Топ-10 питерской осени по пиву, так на первых местах фигня типа Козела. И только на 10-м Кельт черное, которого нет! Крушовица совсем отсутствует в списке.
Короче, НЕДОВОЛЕН.

Java.net blog post

Таки написал очередную статью...
Пишите комментарии!

понедельник, 17 декабря 2007 г.

Luminara

Это простая игра-крошилово...

Если надо расслабиться и отключить все мозги, кроме спинного - самое оно.

пятница, 14 декабря 2007 г.

С Новым Годом!

Сегодня вечером у нас корпоративная пьянка по поводу...
Если не протрезвею, то до встречи в новом году!

Стихи

Когда Мишку одеваем на улицу и надо завязать шапочку под подбородком, мы его обычно спрашиваем: что у нас на потолке? Мишка уже привык отвечать: мухи! Хотя мухи были только летом на даче...
Вот я на днях ему стишок сочинил:
    - Мухи, мухи, где вы там?
    - Мы сидели по домам!
    - Почему вы не летали?
    - Потому что нас не звали...
Юля говорит, что Агния Барто отдыхает... ;)

четверг, 13 декабря 2007 г.

Чайник "Витёк"

Купили себе в МедиаМаркт новый чайник Aquamarine. Уж больно дизайн понравился. И еще есть функция поддержки температуры, которая в принципе, нафиг не нужна...

Показывал Мишке как вода кипит. Заинтересовался.

Воспитание детей

Юля читает соответствующую книжку. Ну а там разные советы:
- Попросите ребенка достать головкой плеча...
- Пусть потрогает ушком стул...
Чувствую, что мысли у меня не в ту сторону думают ;)

среда, 12 декабря 2007 г.

Гироскоп в руке

У нас в Сане сейчас бум на кистевые тренажеры PowerBall. В нашей комнате валяется такая модель (со счетчиком). Я долго был рекордсменом (11604 об/мин), но Леонид побил мой рекорд буквально 5 минут назад (11880 об/мин). Надо дальше тренироваться...
Хороший подарок на Новый Год. Мне, например, такая модель нравится.

Одноклассники

Пили пиво со школьными друзьями: Сергей Шумский, Алексей Матц и Алексей Разницын. Не виделись лет 15!
Хорошо посидели. Выпили весь Guinness в кабаке Медведь. Много о чем поболтали. Собираемся собрать побольше народу на февральский слет выпускников, так как, говорят, что наша классный руководитель последний год работает. Надо бы успеть повидаться. Интересно, что некоторые не поменялись совсем, а других никак не узнать.

День выборов

Выборы! Выборы! Кандидаты - ...
Второго декабря я был в Таллинне. Известная проблема, что половина населения Эстонии - русские, половина из которых - граждане России. Голосовать я в Таллинне не мог, так как зарегистрирован в подмосковье. Но очереди видел.
Первая очередь от консульства России на улице Лай доходила до олененка, поворачивала в сторону улицы Пикк, по которой уходила в даль. Вторая - от гостиницы SAS, что за Домом Торговли, мимо здания парковки уходила в даль по улице Рявала. Концов этих очередей я не видел - было не по пути. Народ, в основном, пожилой. Молодых напрягает стоять в очередях по несколько часов.

Java Puzzle 66: A Private Matter

Что напечатает следующая программа?
class Base {
    public String name = "Base";
}
class Derived extends Base {
    private String name = "Derived";
}
public class PrivateMatter {
    public static void main(String[] args) {
        System.out.println(new Derived().name);
    }
}
Программа не скомпилируется. Дело в том, что поля класса не могут переопределять поля суперкласса как, например, методы. В данном случае класс Derived скрывает поле name класса Base (JLS 8.3). Это корректно, но нерекомендуется, так как противоречит принципу Лискова: если что-то можно делать с базовым классом, то то же самое должно быть возможно делать с его потомком. Чтобы решить проблему с доступом к полю name класса base надо переписать код так:
public class PrivateMatter {
    public static void main(String[] args) {
        System.out.println(((Base) new Derived()).name);
    }
}

Java Puzzle 65: A Strange Sage of a Suspicious Sort

Всю программу приводить не буду. Приведу пример неправильной реализации компаратора, из-за которого вся программа сортировки работает неправильно.
class IntegerComparator implements Comparator {
    public int compare(Integer i1, Integer i2) {
        return i2 - i1;
    }
}
Идиома, лежащая в основе этой имплементации, известна с ранних дней UNIX (1970). Поэтому многие уже не помнят, а остальные не знают, решение этой проблемы. Помните, что компьютерная математика отличается от обычной. И при вычитании большого положительного числа из большого отрицательного числа можно получить положительное, а не отрицательное. Это называется - переполнение разрядной сетки...
Вот правильная имплементация:
class IntegerComparator implements Comparator {
    public int compare(Integer i1, Integer i2) {
        if (i1 > i2) return -1;
        if (i1 < i2) return 1;
        return 0;
    }
}
После анализа кода становится ясно, что этот компаратор предназначен для сортировки в обратном порядке. Так что не надо городить своих классов. Используйте компаратор, входящий в состав библиотеки коллекций:
Collections.reverseOrder()

четверг, 29 ноября 2007 г.

Завтра в Таллинн

Раньше вторника обновлений не ждите!

Тяжело быть безработным

Вот такие новости: Вчера в Юго-западном округе столицы у 38-летней москвички, которая все еще не может найти работу, угнали автомобиль Porsche Cayenne. По словам женщины, в период со 2 по 8 ноября она отсутствовала дома и когда пришла в свой гараж на улице Дмитрия Ульянова, то обнаружила пропажу дорогостоящей иномарки, которая, кстати, была оснащена спутниковой сигнализацией.

суббота, 24 ноября 2007 г.

Tarja Turunen


Не дождавшись похода в магазин загрузил послушать свеженький альбом Тарьи My Winter Storm (2007). Да, блин, это вам не Nightwish. Голос у Тарьи, конечно, шикарный, но вот музыка на альбоме... Странная какая-то музыка. Медленная и печальная. А вот то как она перепела Poison Элиса Купера мне совсем не понравилось.
Короче, музыка под настроение. Слушать долгими зимними вечерами, в одиночестве уставившись в потолок...

Тест: москвич или петербуржец?

Судя по этому тесту мы с Юлей из Питера. Ну я то - понятно, а она от меня, видимо, словечек нахваталась ;)
Может, вы и живете в другом городе, но у вас язык истинного петербуржца
И пусть они там смеются над "курой-гриль" и хрестоматийным "поребриком" — вы выше этого. Вы навсегда — житель культурной столицы, даже если сейчас вы далеко от дома.
Пройти тест

пятница, 23 ноября 2007 г.

Java Puzzle 64: The Mod Squad

Следующая программа генерирует гистограмму чисел по модулю 3. Что она напечатает?
int[] histogram = new int[3];
int value = Integer.MIN_VALUE;
do {
    int index = Math.abs(value) % 3;
    histogram[index]++;
} while (value++ != Integer.MAX_VALUE);
for (int i = 0; i < 3; i++) {
    System.out.println(histogram[i]);
}

Считай - не считай... Но эта программа сгенерирует исключение ArrayIndexOutOfBoundsException: -2
Проблема в том, что метод Math.abs возвращает неотрицательное число всегда, кроме одного случая когда аргумент равен Integer.MIN_VALUE. В этом случае результат тоже равен Integer.MIN_VALUE. А при получении остатка от деления отрицательного числа получается отрицательный остаток. А ведь мы используем его в качестве индекса массива...

Java Puzzle 63: More of the Same

В этой задаче приводится программа, аналогичная предыдущей, но вместо IdentityHashMap используется HashMap:
public class MoreNames {
    private Map map = new HashMap();
    public void MoreNames() {
        this.map.put("Mickey","Mouse");
        this.map.put("Mickey","Mantle");
    }
    public int size() {
        this.map.size();
    }
    public static void main(String[] args) {
        MoreNames map = new MoreNames();
        System.out.println(map.size());
    }
}

Ну почему он возвращает 0? А потому, что первый метод не является конструктором. Случайно добавив возвращаемый тип к декларации конструктора можно долго искать эту ошибку. Аккуратнее! ;)

Traveler IQ Challenge

Забавный тест на знание географии:

Я дошел до седьмого уровня:

четверг, 22 ноября 2007 г.

Квартира

Через год после ремонта наша квартира выглядит вполне обжитой.

Java.net blog post

Таки написал очередную статью...
Пишите комментарии!

Клуб 2м

В одном из магазинчиков нам выдали рекламку "Клуб 2м". Добрались мы до торгового центра Neo на Ладожской. Гуляем, ищем его...
Тут видим - висят джинсы длиной с меня. Вот оно! Этот магазин, в отличии от Богатыря, Больших размеров и т.п., создан не для жырных, а для высоких. Купил куртку с нормальными рукавами! Также купил футболку с длинными рукавами:

Кроме того, в честь открытия подарили еще одну футболку.

среда, 21 ноября 2007 г.

88 минут

Купили недавно новый фильм с Аль Пачино: 88 минут (2007). Очень понравилось! Сюжет закручен очень лихо и мне напомнил фильм Рекрут (2003). Детали раскрывать не буду, но настоятельно рекомендую посмотреть! Аль Пачино очень шикарный актер! Не подкачал...

Обратил внимание, что сейчас готовится видеоигра Схватка (2009) по мотивам фильма Схватка (1995).

Java Puzzle 62: The Name Game

Что напечатает следующая программа и почему?
Map map = new IdentityHashMap();
map.put("Mickey", "Mouse");
map.put("Mickey", "Mantle");
System.out.println(map.size());

Напечатает 1, но почему? IdentityHashMap в отличии от HashMap сравнивает объекты по равенству указателей, не вызывая метода equals, а по спецификации (JLS 15.28) два строковых литерала равны не только по значению, но и по ссылке (interned). Однако, следующая программа покажет возможную проблему:
StringBuilder sb = new StringBuilder("Mickey");
map.put(sb.toString(), "Mouse");
map.put(sb.toString(), "Mantle");
System.out.println(map.size());

Используйте IdentityHashMap очень осторожно, так как этот класс не является имплементацией общего назначения интерфейса Map.

Java Puzzle 61: The Dating Game

Следующая программа использует основные возможности классов Date и Calendar. Что она напечатает?

import java.util.*;

public class DatingGame {
    public static void main(String[] args) {
        Calendar c = Calendar.getInstance();
        c.set(1999, 12, 31); // year, month, day
        System.out.println(c.get(Calendar.YEAR));

        Date d = c.getTime();
        System.out.println(d.getDay());
    }
}

Думаете, что программа напечатает 1999 и 31? А вот и нет! Она напечатает 2000 и 1. Думаете, что нашли проблему 2000 года (Y2K)? А вот и нет! Все гораздо хуже...

Первая ошибка в вызове "c.set(1999, 12, 31);". Классы Date и Calendar представляют года и дни начиная с 1, а вот месяцы - с нуля. Таким образом, тут устанавливается 31 день тринадцатого месяца. Но ведь в календаре всего 12 месяцев и должна быть ошибка типа IllegalArgumentException? Календарь просто пересчитывает дюжины и добавляет 1 за каждую к годам. Хреновая ошибка. Если 12 исправить на 11, то для программы все будет хорошо, но не для того, что читает и сопровождает код! Для человека 11-й месяц - это ноябрь.

Это объясняет почему мы получили 2000 вместо 1999, но почему 1 вместо 31? Читайте документацию: метод getDay возвращает не день месяца, а день недели (0-воскресенье, 1-понедельник и так далее). На что у нас выпадает 31 января 2000 года? На понедельник! Обратите внимание, что соответствующий метод Calendar.get(DAY_OF_WEEK) возвращает значения, начиная с 1, а не с 0.

Будьте очень осторожны, когда используете Date и Calendar. Всегда уточняйте поведение по спецификации!

Попов vs Маркони

Всем в России известно, что радио изобрел Попов. На западе считают, что радио изобрел Маркони. Старая разборка между коммунистами и капиталистами. Но вот появились новые "рассекреченные" данные. И не надоело им пинаться...

Е в рот сеть

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

Day off

Вчера брал отгул. В субботу отработаю...

В прошлый четверг Юле пришла повестка явится в суд... в среду! Специально они что-ли? Ну она позвонила и ей сказали приехать в ГИБДД на Цимбалина. Приемные часы: вт/чт с 15 до 18. Мы приехали туда и ей сказали, что суда еще не было и надо ехать к мировым судьям на бульваре Красных зорь. А там сказали, что суда еще не было и нам нужно придти в 10 утра в следующую среду.

Так мы и катались через улицу Народную, на которой доблестные парни в желтых накидках регулировали движение. Зеленый включали секунд на 30, а красный - минут на 10. Я, конечно, понимаю, что они разгружали Ивановскую/Народную/Славы, так как на КАДе (на вантовом мосту) пробка была из-за аварии. С каждым годом на дорогах все хуже и хуже...

И что самое обидное. У нас права отобрали на трассе Москва-Питер за превышение (на трассе!). А в самом Питере народ носится - и ничего. Мало того, еще и нам бибикает, что мы тащимся со скоростью 60 км/ч (нам GPS напоминает о превышении... зануда:). Например, Шлиссельбургский проспект вечером переходить просто опасно. Даже днем народ умудряется пролетать на красный свет.

понедельник, 19 ноября 2007 г.

Android SDK

Google представила документацию и набор для разработки программного обеспечения (SDK) к своему основанному на Linux стеку для мобильных телефонов Android, а также объявила о начале конкурса для программистов с призовым фондом 10 миллионов долларов. С помощью предложенного SDK разработчики могут создавать приложения для платформы Android на языке программирования Java и запускать их в среде виртуальной машины Dalvik, предназначенной для встраиваемого использования и работающей поверх ядра Linux.

Объявленный конкурс для разработчиков призван стимулировать Open Source-сообщество создавать программное обеспечение для Android. Задача для участников — создать свое любимое приложение для мобильных телефонов. Принимаются программы любого типа, однако приветствуется инновационность и, конечно, полезность разрабатываемых приложений. Среди областей, с которых можно начинать разработку приложений для конкурса Android, выделены такие, как социальные сети, работа с информацией различного типа (например, фотографиями), email/IM/календарь, игры, новости, переосмысление традиционных пользовательских интерфейсов.

Сдается мне, что скоро для мобильников от Google будет гораздо больше ПО, чем сейчас для Window Mobile...

суббота, 17 ноября 2007 г.

Crematory


Недавно купил диск Klagebilder (2006), что переводится как "Картины плача". В отличии от большинства дисков группы альбом на немецком языке. На мой взгляд, это - плюс. Альбом достаточно сильный, обладающий должной хитовостью. Проходных песен, похоже, нет совсем. Даже смена гроула Феликса и чистого вокала гитариста Маттиаса неплохо вписывается. Рекомендую!

пятница, 16 ноября 2007 г.

Java Puzzle 60: One-Liner

Этот вопрос проверяет знание API. Для каждой мини-задачки необходимо написать метод, содержащий только одну строку. Тестируется знание новый фич Java 1.4 и 5. Авторы утверждают, что знание библиотек может сэкономить много времени и увеличить скорость и качество программ. Насчет качества - несомненно, но вот насчет скорости...

A. Напишите метод, принимающий список элементов и возвращающий список элементов в том же порядке, но без дубликатов. Например, передаем список {"spam", "sausage", "spam", "spam", "bacon", "spam", "tomato" и "spam"}, а получаем список {"spam", "sausage", "bacon" и "tomato"}.

Тут необходимо вспомнить про полезный класс LinkedHashSet, базирующийся на классе LinkedHashMap, который сохраняет порядок добавления записей. Метод будет выглядеть следующим образом:
static <E> List<E> noDups(List<E> list) {
    return new ArrayList<E>(new LinkedHashSet<E>(list));
}

B. Напишите метод, принимающий строку, содержащую 0 или больше токенов, разделенных запятой, и возвращающий массив строк, содержащий токены в том порядке, как они встречаются во входной строке.

Если вы подумали про StringTokenizer, то вы очень давно программируете на Java, как и я. В версии 1.4 была добавлена поддержка регулярных выражений (java.util.regex). Давно пора их выучить, так как размер кода существенно сокращается:
static String[] parse(String string) {
    return string.split(",\\s*");
}

C. Напишите метод, который преобразует некоторый многомерный массив к строковому виду, который был бы удобен для целей отладки.

Тут авторы прикололись. Такой метод уже есть в JDK: Arrays.deepToString(Object[]). Кроме него есть еще пара полезных методов: Arrays.deepEquals(Object[],Object[]) и Arrays.deepHashCode(Object[]). И хотя в этом методе не одна строка, наш метод может просто вызывать библиотечный:
static String toString(Object[] array) {
    return Arrays.deepToString(array);
}

D. Напишите метод, принимающий два целых числа и возвращающий true, если у них установлено одинаковое количество бит.

Для целочисленных типов (Integer и Long) в Java 5 были добавлены методы работы с битами. Воспользуемся методом Integer.bitCount(int), который возвращает количество установленных бит в целом числе:
static boolean equals(int one, int two) {
    return Integer.bitCount(one) == Integer.bitCount(two);
}

Java Puzzle 59: What's the Difference?

В задачке используется массив предопределенных значений. Суть задачки не важна, так как сконцентрировавшись на ее решении можно упустить очевидное. Я натыкался на такие проблемы, когда начинал изучать Java. Вот массив значений каждое из которых меньше предыдущего на 111:
int[] values = {
        789, 678, 567, 456,
        345, 234, 123, 012 };
Или нет?

Согласно JLS 3.10.1 целочисленные литералы, начинающиеся с 0 интерпретируются как числа, записанные в восьмеричной системе счисления. Таким образом, последние значение равно 10. Авторы рекомендуют никогда не выравнивать целочисленные литералы с помощью 0. А так хочется иногда иметь красивую табличку в коде!

Тяжелое наследие Fortran и C...
Неужели сейчас кто-то использует восьмеричную систему?

Gmail поддеживает IMAP

Google добавил поддержку IMAP в почтовый сервер. Знаю многих любителей этого дела, но я сам сторонние почтовые клиенты теперь не люблю. Метки рулят!

среда, 14 ноября 2007 г.

Helloween


Перед поиском и покупкой нового альбома решил послушать предыдущий: Keeper of the Seven Keys: The Legacy (2005). Альбом двойной, но общей продолжительностью 76 минут. Половина песен только удалась и переплюнуть первых двух Хранителей им не удалось. Лучше бы склепали однодисковый вариант, выкинув отстойные композиции, которые очень мешают прослушиванию. Музыканты разошлись по разным группам, типа, Gamma Ray и Masterplan. Вроде бы и играют профессионально, но нет у них хороших композиторов и поэтов-песенников...

iGO

Пытаемся пользоваться GPS приемником с помощью iGO. Он все время пытался нас вытащить на Невский, даже когда тот на ремонте был.
Но вчера с утра он повез нас к моему офису (точнее, в центр вакцинации на Фонтанке) через Цимбалина. Доехав до перекрестка Седова-Цимбалина, мы обнаружили, что там все стоит и двигаться не собирается. Я стал командовать, как доехать дворами до Московского вокзала. Там по Невскому он нас довез до Аничкова моста. Там поворота налево нет и он нам порекомендовал ехать через Садовую. Но зная как там забито, мы развернулись на Фонтанке через мост у цирка и по прямой доехали нормально.
Выводы:
1. Короткий путь, обычно, не самый быстрый.
2. Надо найти программу, которая поддерживает информацию о пробках через GPRS.
Кажется, Серега Александров что-то подобное показывал, но она платная для PPC.

Пробки

Брал вчера day off. Надо было свозить Мишку на вакцинацию, записать в детский садик, поменять резину на зимнюю и за посылкой смотаться. Пробки везде!
Мы в обед час простояли пытаясь въехать с Октябрьской набережной на Володарский мост. После того, как свернули с набережной, я вышел, перешел мост, сходил в РОНО, написал анкету для детского садика и вернулся. А Юля только-только на мост въехала...
Потом ехали из дома на Хасанскую через КАД. Вроде все нормально, но встречка стоит. Несмотря на то, что въезды с Мурманского шоссе закрыты.
Вечером час простояли на съезде с моста Александра Невского на набережную, чтобы домой ехать. Тоже мясо.

Quazatron

Я уже писал про Head Over Heels, но вот, пока собирался билд, попробовал Quazatron.
Слишком быстро для меня. Постарел я, постарел...

Эрудит ПК и КПК

Как я уже писал, есть такая игра как Эрудит. Так вот, недавно обнаружил, что версия для ПК обновилась. Кроме того, появилась версия для КПК. Хочу попробовать...
А еще в клубе Scarlett есть еще игры.

понедельник, 12 ноября 2007 г.

Java Puzzle 58: Making a Hash of It

В этой задаче (продолжение предыдущей) авторы добавили метод hashCode(), однако поменяли тип параметра метода equals() с Object на имя класса, используемого в качестве элемента множества HashSet. Естественно, что никакого переопределения не происходит, а происходит перегрузка методов.

В языке Java перегрузка разрешена, но приводит к ошибкам и неразберихе. Читаем секцию 26 все той же необходимой к прочтению книги Effective Java. Начиная с версии Java 5 появилась аннотация @Override, которую авторы рекомендуют использовать. Я, например, включил в IDEA опцию, которая автоматически добавляет эту аннотацию при переопределении метода. Если в супер классе метод поменяет сигнатуру (всякое бывает), то не возникнет скрытого бага - проект просто не скомпилируется и вы найдете проблему за 5 секунд.

Java Puzzle 57: What's in a Name?

Задачка довольна простая. Некий объект используется как элемент множества HashSet. Метод equals() переопределен, а про метод hashCode() забыли.

В общем, автор напоминает 8 секцию его предыдущей книги Effective Java. Я уверен, что эта книга должна быть прочитана каждым Java-программистом, поэтому останавливаться здесь не будем. Скажем просто: переопределяйте метод hashCode() всегда, когда переопределяете метод equals().

Solid State Disk

Такое чувство, что в моем ноуте начинает сыпаться винт. Очень неприятно. Поэтому стал смотреть, на что бы такое его можно заменить...
Оказывается, уже вышел Solid State Disk от Samsung. Правда - дорого пока. Зато, блин, не посыпется, если в дороге стукнешь. А Toshiba начала выпускать ноуты с такими дисками. Но из-за SSD диска цена тоже зашкаливает все разумные пределы.

Myon


Поскреб по сусекам и нашел альбом Ghost In Paradise (2002). Очень добротно сделанный альбом. Как говорится, очередная пятерка очередных финнов...
Достаточно динамичный power metal с кучей мелодичных вставок, которые делают музыку очень приятной слуху. Альбом на твердую четверку, так как не смотря на качество записи и профессионализм музыкантов альбом не цепляет. Да, есть некоторые интересные композиции, но, в основном, под настроение...

четверг, 8 ноября 2007 г.

Метровый негатив

Сегодня что-то дикое в метро творилось. Меня достали настолько, что на ПлАНе я не выдержал. Спускаюсь с эскалатора, а там поезд приехал. Все с этого поезда по всей платформе общей массой рвутся на эскалатор. Те кто спускается с эскалатора в ужасе стоят всех пропускают или прячутся за колонны. Ну я сказал себе, что у нас правостороннее движение и пошел по самой правой стороне. Несколько человек пытались меня сбить, но неуспешно. Масса мне позволяет. Двое особо шустрых очень сильно отлетели обратно в толпу, возмущаясь. Чем - непонятно.
Есть предположение, что автомобилисты-уроды, которые помялись на свежем голольду, спустились в метро и ведут себя как на дороге. Только если на дороге нормальные люди их пропускают, боясь повредить машину, то в метро все совсем по-другому. Хотя может быть это из-за того, что Обводный закрыт и, как пишет Стас, нигде не проехать...
Когда в вагон заходил поразился. Стоит тетка с парнем и огромным чемоданом. Стоит прямо напротив двери. Народ протискивается мимо ругается. Ей сын, видимо, сказал, что подвинуться надо бы. На что тетка громко ответила: "Что я с чемоданом по вагону ходить должна? Пусть остальные обходят!"
Бля!

среда, 7 ноября 2007 г.

Железная дорога

Мои родители подарили Мишке набор Кроха - Железная дорога. Мы докупили еще деталей и получаются различные конфигурации. Мишка очень доволен!

Шкаф для дисков

Шкаф для обуви

Java Puzzle 56: Big Problem

Проверим знание класса BigInteger. Что напечатает следующая программа?
BigInteger value = new BigInteger("1000000");
value.add(new BigInteger("1000000"));
System.out.println(value);

А вот и нет! Не 2 миллиона, а всего 1. Авторы данного API использовали не вполне корректные имена для методов неизменяемого (immutable) объекта, что и вводит пользователей в заблуждение. Чтобы исправить ошибку надо сделать так:
BigInteger value = new BigInteger("1000000");
value = value.add(new BigInteger("1000000"));
System.out.println(value);

Java Puzzle 55: Creationism

Иногда полезно для класса знать количество экземпляров, которые были созданы. Следующая программа демонстрирует эту технику. Что будет напечатано?
public class Creator {
    public static void main(String[] args) {
        for (int i = 0; i < 100; i++)
            Creature creature = new Creature();
        System.out.println(Creature.getCount());
    }
}
class Creature {
    private static long count = 0;
    public static long getCount(String[] args) {
        return count;
    }
    public Creature() {
        count++;
    }
}

Программа не скомпилируется, так как декларация локальной переменной допустима только внутри блока (JLS 14.12-14). Декларацию можно убрать, используя только создание объекта, так как локальная переменная все равно не используется.
Кроме того, авторы не рекомендуют использовать int как тип счетчика, чтобы избежать переполнения. Максимум для типа int - 231 - 1 (около 2.1 * 109), а для типа long - 263 - 1 (около 9.2 * 1018). Сейчас компьютеры способны создавать около 108 объектов в секунду. Следовательно переполнение для типа long произойдет через три тысячи лет.
Также авторы рекомендуют использовать thread-safe вариант:
class Creature {
    private static long count = 0;
    public static long getCount(String[] args) {
        synchronized (Creature.class) {
            return count;
        }
    }
    public Creature() {
        synchronized (Creature.class) {
            count++;
        }
    }
}
В Java 5 и выше можно использовать класс AtomicLong:
import java.util.concurrent.atomic.AtomicLong;
class Creature {
    private static final AtomicLong count = new AtomicLong();
    public static long getCount(String[] args) {
        return count.get();
    }
    public Creature() {
        count.incrementAndGet();
    }
}

вторник, 6 ноября 2007 г.

Стая


Купил в Кайласе диск Страна Льдов (2005). Сначала заинтересовало оформление альбома - очень качественное, как на западных лейблах. Прикинул музыку - вполне добротный тяжелый рок с большим количеством баллад, причем очень качественно сведен. Голос вокалиста очень напоминает Кипелова в его лучшие годы. Лирика русскоязычная, незапоминающаяся, но ведь не это главное...
Главное, что слушать интересно!
Пошукал в интернет и нашел сайт белорусской группы Стая. Во братья славяне дают!
ЗЫ. Кипелов ТАК уже не поет, а Беркут, видимо, и не будет. Да и Ария уже не та...

воскресенье, 4 ноября 2007 г.

Обновление шкафов

Наконец-то нам привезли шкафы и полки, что мы заказали. Поставили пока шкаф для обуви в коридоре, и шкафы для CD и DVD в зале. Очень симпатично выглядит!
Расставлял свои диски - теперь их удобно брать и таскать на работу. Думаю различные обзоры станут чаще появляться, если мне не надоест ;)
DVD влезли вплотную. Как дальше быть - не знаю. Может купить тонкие коробочки, чтобы больше влезло?

С первым снегом

Сегодня с утра обнаружили снег за окном. Мишка ходил, изучал его...

суббота, 3 ноября 2007 г.

КАД - ИКЕА

Сегодня ездили в Мега-ИКЕА. Пройтись по магазинам да на детской площадке поиграться.
Обнаружили, что открылся второй вантовый мост. Теперь выезд на мост гораздо проще, так как там 4 полосы и никто по крайней не едет. Едем в общем потоке... Смотрю на спидометр - там уже 150. Смотрю за окно - пора с моста съезжать. Клево!
В обратную сторону на мосту пока две полосы. Все еще спиливают старое ограждение...
Быстрее бы КАД до Пашки проложили. Так не хочется по Ленинскому ездить.

Пока мы с Мишкой на деской площадке тусовались Юля гуляла по ИКЕА. Накупила всякого...
Пытался понять по чеку, что конкретно мы купили и почем - так и не понял:
БУРКЕН КН+КР 15
ИСИГ САЛФ БУМ 3 (салфетки)
ФЁРВОНА ТНСН РК
СМИККА СУХ БУКЕ (букет сухих цветов)
МЮКЕН ЗЕРК НАСТ (зеркало настольное)
БУРКЕН ДЗТР СХР (дозатор сахара)
КОМПЛИМЕНТ НАБ
БАРНСЛИГ МИНИ-К
БУХОЛЬМЕН ДСК Р (доска разделочная)
КЛАППАР ИГЕЛЬКО
ЭПИСК МСК 14 КР
ИСИГ ГИРЛ 5 М Ж
ИСИГ ГИРЛ 5 М М
НЬЮТА МОЧ Д/ТЕЛ
ФЁРВОНА ТЕНН МЯ
БЕВАРА ЗЖМ Д/ПК (зажимы для пакетов)
ПАТРУЛЬ ОТРАЖАТ (отражатель на одежду)
ШАРМ ТРК КРСН/Ч

Ну что такое Клаппар Игелько?
Шведы, блин....

пятница, 2 ноября 2007 г.

Rammstein - Das Modell

... или Иван Васильевич меняет профессию:

Quazatron

Была на ZX Spectrum одна занятная игрушка. Там нужно было ездить на роботе по трёхмерным уровням, постреливать по другим роботам или брать их на абордаж, во время которого нужно было успеть справиться с некоей вариацией лазерной головоломки за ограниченное время.

И вообще, на этом сайте есть все спектрумовские программы, о которых я вообще что-то слышал. Надо бы попробовать установить эмулятор на Pocket PC. Вот только не знаю, как можно играть стилусом вместо джойстика и клавиатуры...

Новый загранпаспорт

Тут коллега пишет, как надо получать загранпаспорт с минимумом геморроя. Полезная информация. Через пару лет поеду в центральный ОВИР, так как с районными отделениями у меня всегда куча проблем. А в центральном (давным-давно) делал и себе, и бабушке (жительница Эстонии, но гражданка России) без проблем.

Sonata Arctica


Переслушал альбом Reckoning Night (2004). Очень добротный альбом в отличии от следующего...
Первые же аккорды дают понять, что группа не растеряла своей энергетики - настолько "по-сонатовски" быстро открывается этот альбом. Дальше - больше. Композиции звучат мощно и сильно, с неким хэви-металлическим оттенком, но именно они придают этим песням особый шарм. Есть и красивые баллады для романтиков...
Некоторые отрезки звучат настолько необычно для группы, что ее и не узнать. Просто у Sonata Arctica появилось новое звучание. Развивается группа, вот только куда?

Java Puzzle 54: Null and Void

Что произойдет со следующей программой:
public class Null {
    public static void main(String[] args) {
        ((Null) null).hello();
    }
    private static void hello() {
        System.out.println("Hello world!");
    }
}

Сначала можно подумать, что программа сгенерирует NullPointerException. На самом деле выражение используется для вычисления класса, который содержит статический метод, а значение выражения игнорируется.

Но я бы еще больше бы постарался запутать тестируемого:
public class Null {
    public static void main(String[] args) {
        call(null);
    }
    private static void call(Null object) {
        object.hello();
    }
    private static void hello() {
        System.out.println("Hello world!");
    }
}
И совет на будущее. Не используйте ссылки на объекты для вызова статического метода - всегда указывайте имя класса, например:
Integer.toString(10)

Java Puzzle 53: Do Your Thing

Допустим, что есть некоторый библиотечный класс, который нельзя изменить:
public class Thing {
    public Thing(int i) {}
}
Допустим, вам надо отнаследоваться от этого класса следующим образом, чтобы иметь доступным значение, которое передается суперклассу при инициализации:
public class MyThing {
    private final int i;
    public Thing() {
        super(this.i = Generator.getId());
    }
}
Приведенный выше класс не скомпилируется, так как нельзя ссылаться на переменную класса до вызова метода super(). Как можно выкрутиться из этой ситуации, чтобы метод Generator.getId() не вызывался дважды?

Решение использует альтернативный вызов конструктора, описанный в JLS 8.8.7.1:
public class MyThing {
    private final int i;
    public Thing() {
        this(Generator.getId());
    }
    private Thing(int i) {
        super(i);
        this.i = i;
    }
}

Красиво

1 x 8 + 1 = 9
12 x 8 + 2 = 98
123 x 8 + 3 = 987
1234 x 8 + 4 = 9876
12345 x 8 + 5 = 98765
123456 x 8 + 6 = 987654
1234567 x 8 + 7 = 9876543
12345678 x 8 + 8 = 98765432
123456789 x 8 + 9 = 987654321

1 x 9 + 2 = 11
12 x 9 + 3 = 111
123 x 9 + 4 = 1111
1234 x 9 + 5 = 11111
12345 x 9 + 6 = 111111
123456 x 9 + 7 = 1111111
1234567 x 9 + 8 = 11111111
12345678 x 9 + 9 = 111111111
123456789 x 9 + 10= 1111111111

1 x 1 = 1
11 x 11 = 121
111 x 111 = 12321
1111 x 1111 = 1234321
11111 x 11111 = 123454321
111111 x 111111 = 12345654321
1111111 x 1111111 = 1234567654321
11111111 x 11111111 = 123456787654321
111111111 x 111111111 = 12345678987654321

Ваши деньги не доступны

При попытке снятия денег на выходные я обнаружил, что закончился срок действия зарплатной карты. С кредитной снимать наличку - себе дороже, да и ПИН код я не знаю.
Позвонил в Райффейзен банк - мне сказали, что карта перевыпускается автоматически, если на счету достаточно средств. Но сказать, перевыпущена ли карта и в каком отделении ее забирать отказались, мотивируя это тем, что я отказался от предоставления информации по телефону. Я то имел ввиду всякие счета и т.п.
Написал представителю Sun Microsystems в Raiffeisen, чтобы сообщила куда и когда ехать. Очень не хочется потерять пару часов на путешествие по отделениям.

пятница, 26 октября 2007 г.

Lord of the pings

Three pings for the token rings,
Five pings for the UNIX machines,
Hundred pings for the broken links,
One special ping to check them all
Through Simple Network Management Protocol!

English

A panda eats shoots and leaves
Панда ест побеги и листья

A panda eats, shoots and leaves
Панда ест, стреляет и уходит

А всего одна запятая...

Bier König

Вчера сидели в хорошем пивном ресторане "Bier König" (Пивной король) на Гороховой, 40. Все было просто замечательно: и пиво, и еда. Пива огромный выбор. Не только немецкое, но и чешское есть, и ирландское. Одно не понравилось: пока я отлучился в туалет шустрый официант унес недоеденный стейк. Предлагал возместить оплошность пивом, но свою норму я уже выпил.
В ресторане есть телевизоры и народ приходит туда смотреть игры. Вчера, например, был футбол: Зенит играл с Нидерландами. Было шумно, но был и бонус. За забитый гол Зенитом нам принесли по стопке водки. Васисуалий приносил фотоаппарат.
Очень рекомендую посетить!
пт, сб: 11:00-05:00; остальные дни: 11:00-01:00
тел.: 310-95-85

среда, 24 октября 2007 г.

Sonata Arctica


Купил новый альбом Unia (2007). Sonata Arctica в свое время была для меня большим открытием в power metal. Но в последнем альбоме весь их power куда-то делся. Вроде и играют неплохо, но как-то скучно и однообразно. Говорят, что его нужно прослушать еще несколько раз, чтобы зацепило. Попробовать, конечно, можно. Вот, боюсь, толку от этого будет ноль.

Запрещено гадить


Вот такой знак висит на подземном переходе к вокзальным туалетам в городе Таллинн. Если вас поймают, то могут заTRAHVать на 10 000 крон.

17 мгновений весны

Тут какой-то чудик пытается проанализировать Штирлица на примере нелепостей в фильме "17 мгновений весны".
А мы все равно любим нашего штандартенфюрера ;)

IntelliJ IDEA 7

Вышла. Надо будет посмотреть...

Собирается СТАРая команда

copypast.ru - лучший проект РУНЕТА!
А Вы знаете свою норму? »»

суббота, 20 октября 2007 г.

Таллинн: халява

Весь город покрыт WiFi сетями. Почти в каждой кафешке есть открытый доступ. вот и сейчас мы зашли в Stockmann, отправили Мишку на детскую площадку и вышли в сеть. в основном, Юля в сети, но вот и я высунул свой нос. и первым делом - сюда, а после пойду почту читать. В понедельник уже буду на работе. Всем привет!

воскресенье, 7 октября 2007 г.

Туман

Какой сегодня с утра густой туман - соседнего дома не видно.

суббота, 6 октября 2007 г.

Отпуск

Сегодня первый день отпуска. Сначала по Питеру погуляем, потом в Таллинн на недельку смотаемся. Доступ к компу будет очень ограниченный...

четверг, 4 октября 2007 г.

id Software

Небезызвестная id Software недавно выпустила многопользовательский шутер Enemy Territory Quake Wars. И просочилась информация о следующем проекте - Rage.

Rage поведает о нелегкой борьбе главного героя с тоталитарным правительством в постапокалиптическом мире (привет Fallout). В отличие от предыдущих проектов id Software, это первая игра, которая отойдет от привычного "коридорного" стиля, позволив игроку свободно гулять пешком и кататься на машинах по открытым пространствам. Иллюзия свободы станет возможной благодаря новому движку id Tech 5, главная способность которого - отрисовка больших площадей с большим количеством деталей, видимостью до горизонта и безо всяких "тормозов".

id Software не огласила ни дату выхода Rage, ни имя ее издателя. Последнее стало сюрпризом, ведь студия уже много лет сотрудничает с компанией Activision. Судя по тому, что недавно они запустили в Steam почти все свои проекты, начиная с Commander Keen и заканчивая Doom 3: Resurrection of Evil, возможно, что Кармак решил заняться цифровым самиздатом.

Октябрятам - привет!

Так сложилось, что у многих моих знакомых дни рождения в октябре. У Саши Поточкина и Сереги Александрова вчера случился, у Стаса Торгашова - сегодня. 7-го будет 56 лет моему отцу. Всем мои поздравления!

Java.net blog post

Таки написал очередную статью...
Пишите комментарии!

Java Puzzle 52: Sum Fun

class Cache {
    static {
        initIfNeeded();
    }
    private static int sum;
    public static int getSum() {
        initIfNeeded();
        return sum;
    }
    private static boolean inited = false;
    private static void initIfNeeded() {
        if (!inited) {
            for (int i = 0; i <100; i++) {
                sum += i;
            }
            inited = true;
        }
    }
}
class Main {
    public static void main(String[] args) {
        System.out.println(Cache.getSum());
    }
}
Программа напечатает не 4950, а 9900. Это не то, что автор такого класса хотел. Весь прикол в том, что JVM инициализирует статические переменные в классе последовательно. Сначала вызывается статический блок, в котором устанавливается значение sum и inited. Затем пропускается инициализация sum. После чего inited принудительно инициализируется в false. Таким образом, при вызове getSum будет повторно увеличено значение sum. Для того, чтобы этого не произошло, надо объявить sum так:
    private static int sum = 0;
или же объявить inited так:
    private static boolean inited;
А вообще так делать не рекомендуется. Лучше сделать так:
class Cache {
    private static final int SUM = calculate();
    public static int getSum() {
        return SUM;
    }
    private static int calculate() {
        int sum = 0;
        for (int i = 0; i <100; i++) {
            sum += i;
        }
        return sum;
    }
}

Java Puzzle 51: What's the Point

class Point {
    private final int x, y;
    private final String name; // cached at construction time

    Point(int x, int y) {
        this.x = x;
        this.y = y;
        this.name = makeName();
    }
    protected String makeName() {
        return "[" + this.x + "," + this.y + "]";
    }
    public final String toString() {
        return this.name;
    }
}
class ColorPoint extends Point {
    private final String color;

    ColorPoint(int x, int y, String color) {
        super(x, y);
        this.color = color;
    }
    protected String makeName() {
        return super.makeName() + ":" + this.color;
    }
    public static void main(String[] args) {
        System.out.println(new ColorPoint(4, 2, "purple"));
    }
}
Программа напечатает: [4,2]:null
Этот паззл показывает, что возможно получить значение final переменной до того, как она буде проинициализирована. Для того, чтобы избежать этой проблемы, никогда не вызывайте из конструктора те методы, которые можно перекрыть (напрямую или косвенно). Автор ссылается на свою предыдущую книгу Effective Java.
Для решения проблемы с производительностью в данном случае лучше всего использовать lazy initialization:
    public final synchronized String toString() {
        if (this.name == null) {
            this.name = makeName();
        }
        return this.name;
    }
(еще надо убрать final перед декларацией поля name и инициализацию этого поля из конструктора)

четверг, 27 сентября 2007 г.

Growl Karaoke

Если вам нравится петь караоке и вы уважаете тяжелый рок, то попробуйте Growl Karaoke. Даже если вы знаете, что такое Growl, текст может вас очень удивить. Лично меня это караоке на хи-хи пробивает...

среда, 26 сентября 2007 г.

Приехали

Вот мы и приехали из Москвы. Доехали за 12 часов. Получается все быстрее и быстрее. Правда, у Юли права под Тверью поменяли временное разрешение за превышение скорости на 65 км/ч. Дорога только что отремотирована, тачка хорошая, временный знак с ограничением видно плохо...
Автомобильный холодильник температуру держит нормально несмотря на то, что один раз выдернули из розетки и не сразу обнаружили. На обогрев его не тестировали, хотя и такая фишка в нем есть.
Жаль теперь не получится в Таллинн поехать на машине. Или же придется ждать прав месяц. А ведь погода не улучшается...

пятница, 21 сентября 2007 г.

The missile game

Очень забавная флеш-игрушка. Летишь на ракете по длинной трубе, а там препятствия...

четверг, 20 сентября 2007 г.

Java Puzzle 50: Not Your Type

public class Type1 {
    public static void main(String[] args) {
        String s = null;
        System.out.println(s instanceof String);
    }
}
Тут все просто. Оператор instanceof определен так, чтобы возвращать false, когда его левый операнд null. Этим многие пользуются, чтобы не делать дополнительных проверок на null.

public class Type2 {
    public static void main(String[] args) {
        System.out.println(new Type2() instanceof String);
    }
}
Тут задачка посложнее и я пропустил тот факт, что оператор instanceof требует, чтобы оба операнда имели такой тип, чтобы один был подтипом другого. А программа не скомпилится.

public class Type3 {
    public static void main(String[] args) {
        Type3 value = (Type3) new Object();
    }
}
Опять подколка. После предыдущей задачи можно решить, что программа не скомпилится. Так оно и было бы, если бы создавался объект типа String. Но в программе создается Object, наследником которого являются все классы, включая Type3. Однако, при попытке выполнения произойдет исключение ClassCastException.

Java Puzzle 49: Larger Than Life

Что напечатает следующая программа?
public class Person {
    private final int age;
    private static final Person PERSON = new Person();
    private static final int YEAR
        = Calendar.getInstance().get(Calendar.YEAR);
    public Person() {
        this.age = YEAR - 2000;
    }
    public static void main(String[] args) {
        System.out.println("age = " + PERSON.age);
    }
}
А программа напечатает не 7, а -2000!
Программа показывает, что можно наблюдать final static поле до того, как оно будет проинициализировано. И чтобы это исправить надо изменить порядок следования полей: поставить YEAR перед PERSON, так как создание экземпляра Person требует проинициализированной переменной YEAR.

Русский сайт Лема

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

Стройка

Рядом с нашим офисом уже год как строится новое здание центральной налоговой инспекции. Что самое забавное, его строят какие-то южные гастарбайтеры, которые живут прямо в бараках на этой стройке. Наверняка налогов не платят ;-)
Ну а их биотуалеты, видимо, исчерпали свой ресурс и воздух не озонируют...

Пробки

Что-то сегодня на Володарском мосту и в округе офигенная пробка. Видимо из-за того, что на КАДе грузовики покрытие повредили и осталась одна полоса. От дома до налоговой ехал 50 минут. За это время можно было дойти до метро, проехать пару станций и там еще пешочком пройтись. Обратно я так и делал.
Забавный способ объезда пробки по встречке видел. Разворачивается машина на встречку и по ней сдает задо до перекрестка. Там снова разворачивается и впихивается в поток. Уроды!

Налоговая

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

среда, 19 сентября 2007 г.

Я сделаю для тебя ночь

Видимо, в Microsoft работают любители барона Мюнхгаузена. Они активировали черный экран тьмы, который включается после часа работы на нелицензионной Vista.

Балтийский вокзал

Говорят, что Балтийский вокзал перекрыли - ищут бомбу. Народ возвращается в офис, так как на маршрутки не сесть - безумная давка. Оказалось, что один бдительный страж порядка принял за бомбу кипу журналов. Это, конечно, хорошо. Только пассажиры в час пик, я думаю, были очень недовольны. У нас, например, многие из Петергофа работают.

Java Puzzle 48: All I Get Is Static

Тут рассматривается другая прописная истина: статические методы не виртуальны. Авторы перекрывают статический метод класса в его потомке, приводят экземпляр потомка к типу родительского класса и вызывают статический метод. Естественно, что вызывается метод родительского класса. Для избежания таких проблем - никогда не перекрывайте статические методы! А я еще заявлю, что профессионалы никогда не вызовают статический метод используя экземпляр класса. Я бы вообще запретил это на уровне языка.

Java Puzzle 47: Well, Dog My Cats!

Ну про эту задачку я и писать ничего не хочу. Авторы завели в базовом классе статический метод, а в классах-потомках его вызывают и удивляются, почему счетчик увеличивается для обоих экземпляров класса. Естественно! Каждое статическое поле едино как для самого класса, так и для его потомков.

Das Experiment

Есть такой немецкий фильм как Das Experiment. Он снят по мотивам Стэнфордского тюремного эксперимента. Это психологическая драма. Смотрел как-то по телевизору - очень тяжелый фильм. По началу может показаться нудным, но потом цепляет очень сильно. Хотя для любителей ужастиков со спецэффектами - смотреть не на что. Мориц Бляйбтрой (араб Абдул из фильма Достучаться до небес) играет просто супер!
На NoName пробежала ссылка - поставил качаться.

вторник, 18 сентября 2007 г.

Фантазии из песка

Наткнулся на забавный сайт. Там можно скачать несколько интересных видеосъемок, как Ilana Yahav рисует песком раличные картины. Особенно радует динамика - то что постепенно картины меняются...

Nissan Quest

Недалеко от Казанского собора видел новенький Nissan Quest. Очень длинный минивэн. Я бы даже сказал макровэн - машинка явно не для крупных городов...

Бабье лето

Погода нынче отличная. Сегодня ездил в Городской Ипотечный банк за справкой. Это на набереной Мойки рядом с Исакиевским. Оттуда по каналам и мостам шел пешком на работу: Мойка, Грибанал и Фонтанка. Порадовало, что многие старые дома ремонтируют. Минус такой прогулки один: местные собачники заминировали все набережные...

Java Puzzle 46: The Case of the Confusing Constructor

Что делает следующая программа?
public class Confusing {
    private Confusing(Object object) {
        System.out.println("Object!");
    }
    private Confusing(double[] array) {
        System.out.println("Array!");
    }
    public static void main(String[] args) {
        new Confusing(null);
    }
}
Это вопрос по спецификации. Первый из раздела "классические головоломки". Программа скомпилируется и выполнится конструктор, напечатающий Array. В приведенном выше примере оба конструктора можно вызвать, но по спецификации выбирается тот, который более конкретный. Это второй конструктор, так как каждый массив - это объект, но не каждый объект - массив. Для принудительного вызова необходимого конструктора нужно привести аргументы к типу, определенному в списке формальных параметров:
    public static void main(String[] args) {
        new Confusing((Object) null);
    }
Обратите внимание, что если поменять тип первого конструктора в примере на Double (например), то программа не скомпилируется. В идеале, лучше избегать перегрузки конструкторов и методов.

Java Puzzle 45: Exhausting Workout

Проверяются знания рекурсии. Что делает следующая программа?
public class Workout {
    public static void main(String[] args) {
        workHard();
        System.out.println("It's nap time.");
    }
    private static void workHard() {
        try {
            workHard();
        } finally {
            workHard();
        }
    }
}
Забавно, но если метод будет вызывать сам себя, то вы достаточно быстро получите StackOverflowError. Но если использовать блоки try-finally, как в примере, то на ожидание StackOverflowError уйдет 10291 лет. Можно сказать

понедельник, 17 сентября 2007 г.

Ленинградское настроение

Контрабас не попадает
Гитарист всегда лажает
Барабанщик мимо кассы
И не слышно марокасов
Наше шоу - это говно
Но оно такое одно
Но оно такое, такое одно

Опять Raiffeisen

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

Death Drive

Прислали ссылку на Death Drive. Это, похоже, клон старого, доброго Death Track под PocketPC. Интересно, что создатель предлагает игру на халяву. Поставил качаться...

воскресенье, 16 сентября 2007 г.

В чем разница

Как произносится C#?
Программист: Си шарп
Музыкант: До диез

Может подколоть кого-нибудь, например, ГерМиша:
"И как тебе на До диезе программируется?"

суббота, 15 сентября 2007 г.

Московская площадь

Возвращаясь в четверг из кабака шли с Кэпом к метро. И тут приспичило. Ну Кэп сказал, что знает выход: на площади построили туалеты. Ну мы и пошли...
Блин, как давно я там не был! Площадь отремонтировали, сделали фонтанный комплекс, скамеечки поставили, туалеты сделали с двух сторон площади. Облагородили короче. Теперь это любимое место молодежи, катающейся там на скейтбордах и роликах, так как там есть горки и препятствия разные. Короче, стоит съездить посмотреть.
Знай и люби свой город!

Java Puzzle 44: Cutting Class

Рассмотрим следующие классы:
public class Missing {
    public Missing() {
    }
}
public class First {
    public static void main(String[] args) {
        try {
            Missing m = new Missing();
        } catch (NoClassDefFoundError error) {
            System.out.println("Got it!");
        }
    }
}
public class Second {
    public static void main(String[] args) {
        Missing m;
        try {
            m = new Missing();
        } catch (NoClassDefFoundError error) {
            System.out.println("Got it!");
        }
    }
}
Если скомпилировать все три класса, а затем удалить файл Missing.class, то можно обнаружить, что программы First и Second выполняются по разному. Одна из них генерирует исключение NoClassDefFoundError, а вторая печатает Got it!
Можете определить и объяснить, как выполняется каждая из программ?

Программа First содержит удаленный класс только внутри блока try, поэтому можно ожидать, что исключение NoClassDefFoundError будет перехвачено и программа напечатает Got it! Программа Second содержит удаленный класс вне блока try, поэтому можно ожидать, что исключение NoClassDefFoundError не будет перехвачено. Однако, если запустить обе программы, то можно убедится, что они ведут себя совсем наоборот!

Проблема заключается в небольшой разнице в скомпилированном коде. А если необходимо определить, что класс пропал, используйте reflection:
public class Third {
    public static void main(String[] args) {
        try {
            Object m = Class.forName("Missing").newInstance();
        } catch (ClassNotFoundException exception) {
            System.out.println("Got it!");
        }
    }
}
Но самый главный совет: не перехватывайте Error или его подклассы. Эти исключения зарезервированы для проблем, после которых невозможно восстановиться...

Java Puzzle 43: Exceptionally Unsafe

пятница, 14 сентября 2007 г.

Солдат

Пока сидели зашел разговор о фильме Солдат. Оказалось, что Кэп его не видел.
Пересмотрел сейчас. Классный боевик. Каждый раз считаю сколько солдат завалил Курт Расселл и каждый раз сбиваюсь со счета. Из 20 возможных он убил 21 или 22 солдата. Забавно. Ляп на ляпе, но смотрится на одном дыхании. И не один раз. А как они с пареньком мелким играют! Без слов друг друга понимают...
На IMDB пишут, что среди мусора на планете-свалке американский корабль Франклин Рузвельт, самолет F-117X Remora из фильма Executive Decision (1996) и агрегат из фильма Blade Runner (1982). А так же много других приколов, типа карты московского метрополитена...
У меня еще перевод хороший, одноголосый. Мне больше нравится, чем перевод на DVD, который я видел.
- Почему они это делают?
- Они выполняют приказ, сэр.
- Сколько их?
- Осталось 17, сэр.
- Один против 17-ти. Что вы будете делать?
- Я их всех убью!

четверг, 13 сентября 2007 г.

Хорошо посидели

День программиста мы отпраздновали, посидев в неплохом кабачке на площади Конституции. Были Пашка и Кэп. Ринат обещал, но не доехал.
Гиннесс наливают по 170 рублей. Кажется самое дешевое место в городе. Еще есть Килкенни и Крушовице. Народу мало - не то что в центре.
Литр Гиннесса - это пять! А сейчас - спать...

С праздником!

Сегодня 256-й день года. И что из этого следует?
Это же наш профессиональный праздник - День программиста!
Поздравляю всех друзей и коллег!
Да поможет вам F1!
Да сохранит вас F2!
Во имя Ctrl, Alt и Del - RESET!

среда, 12 сентября 2007 г.

Пожар в Рыбацком

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

Korpiklaani

Прикупил тут их альбомчик Voice Of Wilderness (2005). Очень забавный Folk Metal, сочетающая в себе гитарные партии, ударные, флейту, скрипку, клавишные и прочие фолк инструменты. Атмосфера в музыке очень позитивная. Очень удачно выходят у них припевы.
Слушать ее лучше всего попивая пивко в кабаке и танцуя время от времени, как мы это делали в Визите под Lucky Sharks. Расслабляйтесь!

Java Puzzle 42: Thrown for a Loop

Тут авторами была написана большая программа, которая обходила все массивы, содержащиеся в другом массиве. Приводить я ее не буду, расскажу вкратце...
Обход массива был сделан с помощью бесконечного цикла, выход из которого осуществлялся при отлавливании ArrayIndexOutOfBoundsException. И программа работала непонятным образом, так как все такие исключения втихую пропускались. Это первый совет: никогда не используйте исключений для управления циклом, а используйте исключения только для обработки исключительных условий. Этот совет, кстати, был еще в книге Блоха "Эффективное программирование на Java", Item 39.
Второй проблемой в программе было использование оператора & для логического выражения: (3 <= array.length) & (array[2] == 3)
При таком использовании второе выражение вычисляется несмотря на то, что первое имеет значение false. И, естественно, происходит исключение...

Java Puzzle 41: Field and Stream

Копируем содержимое файла. При окончании процесса копировани закрываем потоки. Или нет?
static void copy(String in, String out) throws IOException {
    InputStream input = null;
    OutputStream output = null;
    try {
        input = new FileInputStream(in);
        output = new FileOutputStream(out);
        byte[] array = new byte[1024];
        int count;
        while ((count = input.read(array)) >= 0) {
            output.write(array, 0, count);
        }
    } finally {
        if (input != null) input.close();
        if (output != null) output.close();
    }
}
Ну да! Как и ожидалось при возникновении ошибки при закрытии первого потока второй закрыт не будет. Главный урок этой задачи: обрабатывайте любые проверяемые исключения, которые могут произойти в блоке finally.

Предвыборная суета

Путин принял отставку правительства Михаила Фрадкова. Фондовые рынки просели в ответ на отставку. Блин! А не ожидает ли нас очередной дефолт?

Гонка вооружений

Наши испытали новую авиабомбу объемного взрыва. "Папа всех бомб", как прозвали это чудо наши СМИ, делает "маму всех бомб" по всем параметрам. Тут есть видеозапись, показанная по первому каналу. После таких приколов становится понятно, почему НАТО пугается при приближении наших самолетов, начавших патрулировать воздушное пространство.
Ждем ответный ход американцев. Новая "холодная" война? Или начнется "горячая"?

Apocalyptica in Tallinn

Apocalyptica устраивает тур в поддержку своего нового альбома Worlds Collide (2007). Из турфирмы Визит пришла рекламка на их концерт в Хельсинки, но выйдет дороже, так как еще гостиницу оплатить надо, да и саму турфирму не обделить. Есть вероятность, что мы с Юлей и Мишкой в это время будем гостить у бабушки в Таллинне. Надо попробовать выделить время на концерт.

System Shock


Зашел вчера в Кайлас. Искал чего-нибудь послушать. Случайно увидел диск группы System Shock. Название привлекло тем, что когда-то была такая компьютерная игра. Интересная. Послушал альбом Arctic Inside (2004). Понравилось. Решил взять...
Вечером слушал дома. Наслаждался. Несколько первых песен и последняя очень даже зацепили. Альбом короткий, минут на 40. Надоесть не успевает. Добротный мелодичный death от шведов. Гитарный саунд достаточно тяжёлый, но при этом очень мелодичный. Вокал - стандартный гроулинг, но не напрягающий.
Понравилось настолько, что хочу найти их второй альбом Escape (2006). Говорят он еще лучше первого...

Масяня

Что-то Куваев размахнулся. Новый мульт на 7 метров выпустил. Самый длинный, говорит...

вторник, 11 сентября 2007 г.

Opeth


Купил альбом Ghost Reveries (2005). На этом альбоме снова появляется превосходный глубокий гроул и сочные гитарные риффы. Так же слух радует наличие лирических акустических вставок. Воистину мастерское владение каждого участника группы своими инструментами разбавляют и вносят в каждую песню неповторимые и разнообразные ходы. Альбом богат всяческими переходами и измененем звучания практически в каждой композиции. Еще бы! Там 4 композиции из 8 продолжительностью более 10 минут.
Пожалуй, на данный момент это наиболее интересный диск Opeth. Здесь нет легко запоминающихся мелодий и рефренов. Есть профессионализм и мастерство, высочайший уровень техники исполнения и нестандартность музыкального мышления. Супер!

Java Puzzle 40: The Reluctant Constructor

Вот, блин, навернули:
public class Reluctant {
    private Reluctant instance = new Reluctant();
    public Reluctant() throws Exception {
        throw new Exception("I'm not coming out");
    }
    public static void main(String[] args) {
        try {
            Reluctant r = new Reluctant();
            System.out.println("Surprise!");
        } catch (Exception e) {
            System.out.println("I told you so");
        }
    }
}
А StackOverflowError получить не желаете? Дело в том, что поля класса инициализируются перед исполнением содержимого конструктора. Вот так и зацикливаемся...
Обратите внимание, что конструктор должен декларировать все проверяемые исключения, которые могут возникнуть не только в теле конструктора, но и в процессе инициализации полей класса.

Java Puzzle 39: Hello, Goodbye

Что напечатает следующая программа?
try {
    System.out.println("Hello");
    System.exit(0);
} finally {
    System.out.println("Goodbye");
}
System.exit останавливает выполнение текущего потока и всех других в текущей позиции. Даже finally блок не имеет права продолжать работу. Если очень надо, чтобы программа выполняла некоторые действия при завершении работы виртуальной машины - используйте shutdown hooks:
System.out.println("Hello");
Runtime.getRuntime().addShutdownHook(
    new Thread() {
        public void run() {
            System.out.println("Goodbye");
        }
    }
);
System.exit(0);

Хайям о нас

Мир я сравнил бы с шахматной доской:
То день, то ночь. А пешки? – мы с тобой.
Подвигают, притиснут, – и побили,
И в темный ящик сунут на покой.

NetApp vs Sun

В среду компания Network Appliance подала патентный иск против Sun Microsystems. В заявлении, поданном в окружной суд в Техасе, ответчику вменяется нарушение семи патентов Network Appliance, касающихся систем обработки данных и связанного с ними программного обеспечения.
Интересно, а sin(x) запатентован?
Истец требует компенсации нанесенного ущерба и просит, чтобы суд вынес бессрочный судебный запрет, который не позволит Sun распространять запатентованную технологию NetApp в составе существующих и будущих версий систем обработки данных и ПО и продолжать дальнейшие разработки файловой системы ZFS.
О как! Давайте патентами инновации глушить...
В Network Appliance уверяют, что пытались решить конфликт с Sun мирным путем, но та заняла агрессивную позицию и отказалась признать свою вину. Network Appliance ничего не оставалось, как обратиться в суд. В своем иске компания не только предъявляет обвинения Sun, но и требует, чтобы суд признал, что сама NetApp не нарушала трех патентов Sun, и объявил их недействительными.
А сами-то нарушили. Лицемеры!

понедельник, 10 сентября 2007 г.

Google + Microsoft

Неужели Google и Microsoft подружились? Google предлагает скачать IE7 со встроенной панелью Google со своего сайта.

Играем мускулами

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

Java Puzzle 38: The Unwelcome Guest

Авторы наворотили безумную программу, высосанную из пальца, так как нормальные программисты так не пишут. Вкратце, рассмотрим следующий код:
public class UnwelcomeGuest {
    private static final long ID;
    static {
        try {
            ID = getID(); // can throw an exception
        } catch (Exception exception) {
            ID = -1;
        }
    }
}
Проблема тут в том, что blank final поле может быть инициализирована только в том месте программы, где она действительно неинициализирована. Но компилятор не может определить, что первое присваивание недостижимо. Авторы рекомендуют создать статический метод для вычисления значения поля:
public class UnwelcomeGuest {
    private static final long ID = calcID();
    private static long calcID() {
        try {
            return getID(); // can throw an exception
        } catch (Exception exception) {
            return -1;
        }
    }
}
Плюсом этого подхода является то, что вычисление значения константы вынесено в отдельный метод, для которого можно написать документацию (что, как и почему)...

пятница, 7 сентября 2007 г.

Java Puzzle 37: Exceptionally Arcane

Что вы думаете об этой программе?
public class Arcane1 {
    public static void main(String[] args) {
        try {
            System.out.println("Hello world");
        } catch (IOException exception)
            System.out.println("I've never seen println fail");
        }
    }
}
А она не компилится! Правильно. Спецификация гласит, что не должна выполняться компиляция блока catch для проверяемого исключения типа E, если соответствующий блок try не может сгенерировать исключение этого типа или одного из его подтипов (JLS 11.2.3).

А что вы думаете о следующей программе?
public class Arcane2 {
    public static void main(String[] args) {
        try {
            // If you have nothing nice to say, say nothing
        } catch (Exception exception)
            System.out.println("This can't happen");
        }
    }
}
А вот и нет! Она компилится. Дело в том, что для базовых типов исключений (Throwable и Exception) сделано исключение, так как они могут использоваться для перехвата непроверяемых исключений.

Попытаемся создать метод, в сигнатуре которого определены проверяемые исключения, но сам он их не кидает. И попробуем его вызвать без проверки. Скомпилится?
interface Type1 {
    void f() throws CloneNotSupportedException;
}
interface Type2 {
    void f() throws InterruptedException;
}
interface Type3 extends Type1, Type2 {
}
public class Arcane3 implements Type3 {
    public void f() {
        System.out.println("Hello world");
    }
    public static void main(String[] args) {
        Type3 t3 = new Arcane3();
        t3.f();
    }
}
Множество проверяемых исключений, которые метод может сгенерировать, является пересечением множеств проверяемых исключений, которые определены во всех типах. Заметьте, не объединение, а пересечение!

Total control

Военные тоже включились в гонку за технологиями, позволяющими контролировать человека. В начале августа Министерство обороны США профинансировало контракт на разработку специальных микрочипов, которые можно будет имплантировать в мозги солдатам и постоянно отслеживать состояние их здоровья. На своем ноутбуке офицер будет видеть, сколько процентов здоровья осталось у каждого бойца, так что сможет эффективнее распоряжаться имеющимися силами. По-видимому, это первый этап на пути к созданию солдата будущего, которым можно управлять через компьютер.

По-видимому, автор заметки переиграл в Quake. Проценты здоровья...
Ха!

Raiffeisen

Ходил пару недель назад в банк. После того, как я закончил свои дела, я спросил операционистку: можно ли оформить кредитную карту? Мне сказали, что надо принести справку с места работы. В бухгалтерии мне сказали, что в первый раз слышат про такую справку и созвонились с представителем банка, работающим с нашей фирмой. Выяснилось, что девушка была новенькая и не знала, что я корпоративный клиент. Ну да ладно. Мне сказали, чтобы я взял паспорт и мне все там оформят.
Сегодня с утра пришел в банк. Все операционисты заняты, двое по телефону болтают. Тут парень какой-то трубку повесил и сидит, делает вид, что меня нет. Ну я двигаюсь ближе, еще ближе. Наконец, он меня заметил. Я спросил про кредитку. Он решил меня послать опять на работу. Я сказал, что я корпоративный клиент. Тогда он выдал мне анкету и сказал, что бы я валил и возвращался, когда заполню анкету и сделаю копию паспорта. Ну я и пошел. В шоке...
По пути, конечно, успокоился, обдумал все. Копию паспорта они всегда делали. Анкеты я всегда с операционистом заполнял. И только этот урод попался! Теперь придется третий раз идти...

четверг, 6 сентября 2007 г.

PocketPref

Некоторое время назад поддержал еще одного отечественного произодителя - купил карманный преферанс.
А дело было так. По пятницам мы на работе пишем пульку. Но меня все обыгрывали. И я решил попрактиковаться. Так как за компом я обычно работаю, то очень неудобно играть в Марьяж. Поэтому купил лицензионный диск и поставил себе на коммуникатор. Много тренировался - пошел в плюс. Статистика лежит на Google Docs. Потом тренировки забросил, когда у коммуникатора случился полный сброс (упал на пол). Теперь переустановил. Надо тренироваться. Завтра - игра!

Java Puzzle 36: Indecision

Что возвращает следующий метод, true или false?
boolean isValid() {
    try {
        return true;
    } finally {
        return false;
    }
}

Метод вернет false, согласно JLS 14.20.2: в выражении try-finally блок finally всегда выполняется, когда управление уходит из блока try. Авторы рекомендуют никогда не покидать блок finally с помощью return, break, continue or throw. Это небезопасно!

Java Puzzle 35: Minute by Minute

Следующая программа имитирует простые часы:
int minutes = 0;
for (int ms = 0; ms < 60*60*1000; ms++)
    if (ms % 60*1000 == 0)
        minutes++;
Программа считае миллисекунды, добавляя время от времени минуты. И чему будет равно количество минут в конце цикла?

А вот и нет! В часе получается не 60 минут, а 60000. А проблема в том, что % и * равнозначные операторы. Т.е. сначала выполняется ms % 60, и 0 тут получается гораздо чаще, чем ms % (60*1000). Как сделать правильно? Заменить все магические числа на константы:
int MS_PER_HOUR = 60 * 60 * 1000;
int MS_PER_MINUTE = 60 * 1000;
int minutes = 0;
for (int ms = 0; ms < MS_PER_HOUR; ms++)
    if (ms % MS_PER_MINUTE == 0)
        minutes++;

Пользователей може запутать, что вокруг % находятся пробелы, а вокруг * - нет. Компилятору до них никакого дела нет. Никогда не используйте пробелы для группировки операторов. Используйте скобки!

Lingvo 11

Купил год назад Лингво 11. Поддержал, так сказать, отечественного производителя. Активно использую. Иногда, для обычных слов открывает дополнительные окошки с нецензурным сленгом. Сейчас сразу не вспомнить, но было пару раз. На работе использую Tutor, который выдает слова на английском или на русском, а к ним нужно набрать перевод. Вещь удобная. Особенно на коммуникаторе. К нам приехали коллеги из штатов, так во время разговора можно быстро найти перевод. Чаще всего с русского на английский.
Ставил тут его на домашний компьютер. Он мне заявил, что неплохо было бы купить 12-ю версию. Залез на сайт. Сравнил. Сейчас напишу, что понравилось.

  • В новой версии они написали Tutor под PocketPC. Гораздо удобнее, когда карточки слов всегда собой, например, в метро.

  • Обновили поиск: теперь включается полнотекстовый поиск, если слово не найдено. Также можно искать по маске, если не уверен в написании слова.

  • Сделана полная интеграция в Windows: при наведении курсора мыши на слово в любом приложении всплывает окошко с его переводом.

  • Есть европейская версия с дополнительными языками: немецкий, французский, итальянский и испанский. И есть многоязычная версия, где помимо указанных языков есть китайский, турецкий, украинский и латинский.


Вот и думай, не поддержать ли отечественного производителя еще раз.

Налоговые вычеты

Занимаюсь возвратом денег с налоговой. Тот еще геморрой. В налоговой дали кучу каких-то бумажек и сказали заполнять. На стендах ничего не нашел по приобретенной недвижимости. Долго вникал в непонятные закорючки и, если бы не программа "Декларация 2006", то уже сошел бы с ума...
БЮРОКРАТЫ!

среда, 5 сентября 2007 г.

Негатив

Выруливаю из метро сегодня вечером. Настроение хорошее. Лечу на крейсерской скорости домой. Тут около метро меня девчока останавливает, типа, па-ма-ги-те. Буркнул в ответ, типа, не ко мне. Лечу дальше. Пролетаю через сквер. Темно. Фонарей нет. Чувак подруливает, типа, братишка не уделишь пару минут драгоценного времени. А еще двое невдалеке пасутся. Ну я говорю "нет" и улетаю. Он в догонку кричит "я, кажется, тебя знаю". Хрен с ним. Перехожу перекресток. Мне на перерез какая-то тетка выбежала и дорогу перегородила. Остановилась, типа, ждет меня. Но я сделал финт ушами, срезал угол и даже не знаю, чего она от меня хотела. Задолбали. Я что? медом намазан?