Заработай на задачках

Существует достаточно простая утилита recode, которую можно установить в Debian следующим образом:
# apt-get install recode

После установки можно легко сменить кодировку любого файла, к примеру с CP866 на utf-8:
$ recode cp866..utf-8 file_name.txt

На момент написания статьи версия Android Studio – 2.2.3. Но, в принципе, подобный способ установки будет работать и в более старших версиях.

  1. Качаем дистрибутив Android Studio с официального сайта.
  2. Распаковываем архив:
    $ unzip android-studio-ide*.zip
  3. Перемещаем папку с IDE в /opt:
    # mv android-studio /opt/
  4. Добавляем группу anroiddev:
    sudo groupadd androiddev
  5. Меняем владельца-пользователя и владельца-группу папки /opt/android-studio:
    # chown -R root:androiddev /opt/android-studio
  6. Даём возможность пользователям в группе androiddev права на запись для папки с IDE:
    # chmod g+w /opt/android-studio
  7. Добавляем своего пользователя (ozi) в группу androiddev:
    sudo usermod -a -G androiddev ozi
  8. Делаем ссылку на скрипт запуска Android Studio IDE:
    # ln -s /opt/android-studio/bin/studio.sh /usr/bin/android-studio

Теперь можно запускать IDE с помощью комманды:
$ android-studio

Кроме того, Android Studio сможет самостоятельно обновляться, когда ей это потребуется.

Бонус, скрипт которым можно заменить ссылку /usr/bin/android-studio:
#!/bin/sh android_group="androiddev" validation_result=`groups $USER | grep $android_group` if [ -z "$validation_result" ] then echo "Пользователь $USER не принадлежит группе $android_group," echo "некоторые функции Android Studio могут работать некорректно." echo "Добавьте его коммандой:" echo "# usermod -a -G $android_group $USER" echo "и повторите запуск IDE." exit fi exec /opt/android-studio/bin/studio.sh

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

Условие задачи

Создать ООП-модель для следующей предметной области:

  1. Калькулятор простой. Выполняет четыре арифметические операции: сложение, вычитание, умножение, деление.
  2. Калькулятор простой с памятью. Выполняет четыре арифметические операции и имеет одну ячейку памяти. С данной ячейкой памяти калькулятор выполняет пять операций: очистить ячейку памяти, записать в ячейку памяти текущее значение, присвоить текущему значению содержимое ячейки памяти, увеличить или уменьшить значение в ячейке памяти на текущее значение.
  3. Калькулятор инженерный. Выполняет четыре арифметические операции и вычисляет значения трех функций: косинус, экспонента, корень квадратный.
  4. Калькулятор инженерный с памятью. Это комбинация пунктов 2 и 3.

Создать консольное приложение с единственным аргументом командной строки – имя входного файла.
Структура входного файла: строка 1 – тип калькулятора, остальные строки – числа и операции для вычисления выражения, при этом каждое данное находится в одной строке. Все операции для вычислений происходят последовательно. Например, содержимое файла для выражения cos(5*7-2)+1, которое необходимо вычислить инженерным калькулятором, может иметь вид:

3 5 * 7 - 2 cos + 1

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

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

Требования:

  • Использовать объектно-ориентированный подход для описания сущностей предметной области.
  • Приложение должно быть консольным. Не использовать графический интерфейс!

Предпочтения по выбору языка программирования: 1) Java; 2) C++; 3) другой ООП язык.

Решение

Выложу один класс для ознакомления и архив с полным решением + тесты:

/* CalculatorBuilder.java */ package ru.ozi_blog.task.calc; import ru.ozi_blog.task.calc.primitives.CalcPrimitive; import ru.ozi_blog.task.commands.binary.*; import ru.ozi_blog.task.commands.nullary.*; import ru.ozi_blog.task.commands.unary.*; import ru.ozi_blog.task.exceptions.BuildCalculatorException; /** * The class CalculatorBuilder takes over the process of creating an object of * the class Calculator. A correct build sequence: * <ul> * <li>Director makes a new object of the class Calculator or MemoryCalculator ( * {@link #newCalculator(CalcPrimitive)} or * {@link #newMemoryCalculator(CalcPrimitive)});</li> * <li>Director adds operations to the object ({@link #addBaseCommands()}, * {@link #addMemoryCommands()}, {@link #addScientificCommands()});</li> * <li>Director gets the ready object ({@link #getCalculator()}).</li> * </ul> * * @see ru.ozi_blog.task.calc.Calculator * @see ru.ozi_blog.task.calc.MemoryCalculator * * @author Zhukavets Aleh * * @param <T> * the type of a number that can be used by a Calculator or * a MemoryCalculator */ public class CalculatorBuilder<T extends Number> { /** * An object to build */ private Calculator<T> newCalc = null; /** * Makes a new object of the class Calculator * * @param calcPrimitive * will be used in the creation of the object */ public void newCalculator(CalcPrimitive<T> calcPrimitive) { newCalc = new Calculator<T>(calcPrimitive); } /** * Makes a new object of the class MemoryCalculator * * @param calcPrimitive * will be used in the creation of the object */ public void newMemoryCalculator(CalcPrimitive<T> calcPrimitive) { newCalc = new MemoryCalculator<T>(calcPrimitive); } /** * Adds basic arithmetic operations to object * * @throws BuildCalculatorException * if an object is not be made */ public void addBaseCommands() throws BuildCalculatorException { if (newCalc == null) throw new BuildCalculatorException(); newCalc.addCommand("+", new PlusSimpleCommand<T>(newCalc.getCalcPrimitive())); newCalc.addCommand("-", new MinusSimpleCommand<T>(newCalc.getCalcPrimitive())); newCalc.addCommand("*", new MultiplicationSimpleCommand<T>(newCalc.getCalcPrimitive())); newCalc.addCommand("/", new DivisionSimpleCommand<T>(newCalc.getCalcPrimitive())); } /** * Adds scientific operations to object * * @throws BuildCalculatorException * if an object is not be made */ public void addScientificCommands() throws BuildCalculatorException { if (newCalc == null) throw new BuildCalculatorException(); newCalc.addCommand("sqrt", new SqrtUnaryCommand<T>(newCalc.getCalcPrimitive())); newCalc.addCommand("exp", new ExpUnaryCommand<T>(newCalc.getCalcPrimitive())); newCalc.addCommand("cos", new CosUnaryCommand<T>(newCalc.getCalcPrimitive())); } /** * Adds memory operations to object * * @throws BuildCalculatorException * if an object is not be made or the object is not the * MemoryCalculator */ public void addMemoryCommands() throws BuildCalculatorException { if (newCalc == null) throw new BuildCalculatorException(); /*if an object can't be converted to a MemoryCalculator object, thrown exception*/ MemoryCalculator<T> tmp = null; if (newCalc instanceof MemoryCalculator) { tmp = (MemoryCalculator<T>) newCalc; } else { throw new BuildCalculatorException(); } tmp.addCommand("import", new ImportMemoryCommand<T>(tmp.getMemory(), tmp.getCalcPrimitive())); tmp.addCommand("export", new ExportMemoryCommand<T>(tmp.getMemory(), tmp.getCalcPrimitive())); tmp.addCommand("clear", new ClearMemoryCommand<T>(tmp.getMemory())); tmp.addCommand("plus", new PlusMemoryCommand<T>(tmp.getMemory(), tmp.getCalcPrimitive())); tmp.addCommand("minus", new MinusMemoryCommand<T>(tmp.getMemory(), tmp.getCalcPrimitive())); } /** * Returns the ready object * * @return the ready object * @throws BuildCalculatorException * if an object is not be made */ public Calculator<T> getCalculator() throws BuildCalculatorException { if (newCalc == null) throw new BuildCalculatorException(); Calculator<T> tmp = newCalc; newCalc = null; return tmp; } /* * (non-Javadoc) * * @see java.lang.Object#toString() */ @Override public String toString() { return "CalculatorBuilder [newCalc=" + newCalc + "]"; } }

Архив с решение и тестами