13 августа 2011 13.08.11 17 2201

Туториал по java №3.5

+8

<< >>

Начнем с разбора проги от Elsemen

import java.util.Scanner;
    public class Calculator {
     

public static void main(String[] args) {
                    double n1;
                    int num;
            Scanner scan = new Scanner(System.in);
                    System.out.print(«1. +\n» + «2. -\n» + «3. *\n» + «4. /\n» + «5. sin(x)\n»);
                    System.out.print(«Make your choise:\n»);
                    num = scan.nextInt();
                    if ((num > 5) || (num < 1))
                            System.out.print(«Error»);
                            else if (num == 5)
                                     {
                                            System.out.print(«Enter a number: x= „);
                                            n1 = scan.nextDouble();
                                            System.out.print(“sin(» + n1 + ") = " + Math.sin(n1));
                                     }           
                                            else
                                            {
                                                    double n2;
                                                    System.out.print(«Enter first number\n»);
                                                    n1 = scan.nextDouble();
                                                    System.out.print(«Enter second number\n»);
                                                    n2 = scan.nextDouble();
                                                    if (num == 1)
                                                            System.out.print(n1 + " + " + n2 + " = " + (n1+n2));
                                                                    else if (num == 2)
                                                                            System.out.print(n1 + " — " + n2 + " = " + (n1-n2));
                                                                            else if (num == 3)
                                                                                    System.out.print(n1 + " * " + n2 + " = " + (n1*n2));
                                                                                            else if (num == 4)
                                                                                                    System.out.print(n1 + " / " + n2 + " = " + (n1/n2));
                                            }
            }
     

}

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

System.out.print(«1. +\n» + «2. -\n» + «3. *\n» + «4. /\n» + «5. sin(x)\n»);
Можно заменить на
System.out.print(«1. +\n2. -\n3. *\n4. /\n5. sin(x)\n»);
Хоть так оно выглядит совсем некрасиво, зато быстрее. Хотя в этой ситуации я бы оставил меню как есть, современные компы прощают и не такие замедлялки, а код гораздо читабельнее (но при разработке на java для телефона лучше действовать эффективнее).

И второе — проверка (num > 5) || (num < 1) может быть удалена. Просто пробегаем по всем значениям num от 1 до 5, а если ничего не сработало – пишем error. Но и тут есть спорный момент: моя конструкция выгодна при небольшом кол-ве условий и редких ошибках ввода, а Elsemen’а наоборот.

Комментарии

[и опять не в тему]
Как и в любом ЯП, в java можно сохранять комментарии – обычно пояснения к коду:
// Комментарий до конца строки
/*
Комментарий на
много
строк
*/

switch

Эта вещь, сконструированна как будто специально для таких меню!

В общем виде он выглядит так(num – цельночисленная переменная):

switch(num){
case 1:{
        //Если num == 1
        break;
}
case 2:{
        //Если num == 2
        break;
}
default:{
        //Если num != ни 1, ни 2
        break;
}
}

Эта штука работает быстрее обеих вышеописанных архитектур меню, да и выглядит красивее!

Таким образом калькулятор (без синуса) стал выглядеть вот так:

import java.util.Scanner;

public class Tutorial {

public static void main(String[] args) {
                double n1, n2;
                int num;
                Scanner scan = new Scanner(System.in);
                System.out.print(«1. +\n» + «2. -\n» + «3. *\n» + «4. /\n»);
                System.out.print(«Make your choise:\n»);
                num = scan.nextInt();
                System.out.print(«Enter first number\n»);
                n1 = scan.nextDouble();
                System.out.print(«Enter second number\n»);
                n2 = scan.nextDouble();
                switch (num) {
                case 1: {
                        System.out.print(n1 + " + " + n2 + " = " + (n1 + n2));
                }
                case 2: {
                        System.out.print(n1 + " — " + n2 + " = " + (n1 — n2));
                }
                case 3: {
                        System.out.print(n1 + " * " + n2 + " = " + (n1 * n2));
                }
                case 4: {
                        System.out.print(n1 + " / " + n2 + " = " + (n1 / n2));
                }
                default: {
                        System.out.print(«Error»);
                }
                }
        }

}

Тут есть пара неудобностей:
1) Должно быть одинаково аргументов(иначе еще одно условие приплетается)
2) В случае ошибки пользователь вынужден ввести 2 числа (ну тут я скажу так: “НУБ ДОЛЖЕН СТРАДАТЬ!”). Зато нам проще и на производительности не сказалось :-)

P.S.: Как вы уже заметили, eclipse сам расставляет табуляцию. Но я советую вам привыкать к табуляции по команде Sourse->Format(Ctrl+Shift+F)

В этом же меню есть команда Organize imports(Ctrl+Shift+O), она поможет, когда будет много импортов


Лучшие комментарии

(num > 5) || (num < 1)

Эту проверку пришлось поставить как раз чтоб нуб не страдал (:
Ты ж сам сказал — «Программа должна быть дружественна к пользователю» xDD
Ибо по другому не придумалось как разрешить проблему с вводом всего одного числа для синуса, ну и если ошибка, чтоб числа не запрашивались…
и сразу же вопрос-есть ли способ обойти ограничение на string в оп-ре switch? ( после c# это просто убивает...)
Та ну не! на вкус фломастеры одинаковые… Ну во всяком случае те, что на спирту (:
Это мне определенно нравится)
если напишешь исходник, то подумаю над обходным путем.

попробуй тупо написать в кейс хеш-код от строки
На счёт бесссмысленности не согласен, но это надо уже углубляться(в c# активно использовалось при обработке значний textbox, например, да и все, в общемто, сейчас расстраиваются, что в 7йjava эту возможность не добавили).

А прога, выводящая что то длиннеее, чем «A».hashCode() заведомо ошибочна, потому что исходя из формулы вычисления хэш-кода, одинаковые значения могут получаться для разных стрингов.
Ну я имел ввиду чтобы программа объясняла пользователю, как, когда, сколько и как сильно ему страдать :D
Собственно, исходник то банальнейший(язык только начал изучать), что то вроде

public static void main(String[] args) {

                Scanner sc = new Scanner(System.in);
                System.out.println("Input string");
                String str = sc.nextLine();
               
                switch (str.hashCode()) {
                case "A".hashCode(): {
                        System.out.println("A was input");
                }
                case "B".hashCode(): {
                        System.out.println("B was input");
                }
                       

                }

        }


Писать в кейс хеш-код-это как то громоздко, имхо
по поводу разных стрингов — да, конечно. например для «Привет» и «RTHnрвЕЕ»

текстбоксы и свободный ввод конечно круто, но радиобаттон никто не отменял. или, на худой конец, чекбокс.

Хотя да, это промашка разрабов, не могу не согласиться…
Подобная прога — бессмысленна. В подобных вещах максимум 3-4 команды, и конструкциями if(){}else if(){} else if(){} можно обойтись. Если нужно именно через кейс — пишешь прогу, выводящую «A».hashCode(), копируешь значение и пишешь (в данном случае) case 65:…
Не работает, пишет, что выражения в кейсах жолжны быть константными(что, вообще странно, но факт). Обещали, вродь в 1.7 добавить, но увы.
Читай также