Защищенное деление

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
11 messages Options
Reply | Threaded
Open this post in threaded view
|

Защищенное деление

Yuriy Mironenko
Вот я что-то туплю, похоже, несусветно. Какой простейший и
наикрасивейший способ сделать "защищенное деление" на Pharo/Squeak? Ну
то есть типа (a/b), при этом чтобы возвращался nil, если a=nil, b=nil
или b=0.

Сначала я написал монстра

<pre>
a ifNil:[nil]
        ifNotNilDo:[:a1|
                b
                        ifNil:[nil]
                        ifNotNilDo:[:b1|
                                (b1=0)
                                        ifTrue: [nil]
                                        ifFalse: [a1/b1]
                        ]
        ]
</pre>

и он работал, но он же монстр! Потом я попробовал что-то типа

<pre>
[a/b] ifCurtailed:[nil]
</pre>

и вот оно уже не работало, хотя

<pre>
[a/b] on:ZeroDivide do:[nil].
</pre>

работало, но только на предмет деления на ноль.

А нужно это для расчётов типа "цена-количество-сумма" или там "рубли-
курс-валюта".

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Igor Stasenko
[ nil / nil ] ifError: [nil]

2010/5/27 Assargadon <[hidden email]>:

> Вот я что-то туплю, похоже, несусветно. Какой простейший и
> наикрасивейший способ сделать "защищенное деление" на Pharo/Squeak? Ну
> то есть типа (a/b), при этом чтобы возвращался nil, если a=nil, b=nil
> или b=0.
>
> Сначала я написал монстра
>
> <pre>
> a ifNil:[nil]
>        ifNotNilDo:[:a1|
>                b
>                        ifNil:[nil]
>                        ifNotNilDo:[:b1|
>                                (b1=0)
>                                        ifTrue: [nil]
>                                        ifFalse: [a1/b1]
>                        ]
>        ]
> </pre>
>
> и он работал, но он же монстр! Потом я попробовал что-то типа
>
> <pre>
> [a/b] ifCurtailed:[nil]
> </pre>
>
> и вот оно уже не работало, хотя
>
> <pre>
> [a/b] on:ZeroDivide do:[nil].
> </pre>
>
> работало, но только на предмет деления на ноль.
>
> А нужно это для расчётов типа "цена-количество-сумма" или там "рубли-
> курс-валюта".
>
> --
> http://groups.google.ru/group/sugr



--
Best regards,
Igor Stasenko AKA sig.

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Alexander Batalshikov
In reply to this post by Yuriy Mironenko
a ifNotNil: [b ifNotNil: [ b ~= 0 ifTrue: [a / b]]].

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Alexander Batalshikov
[a / b] ifError: [nil]

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Dmitry Zamotkin
In reply to this post by Yuriy Mironenko
^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый
короткий и правильный код на ST, гарантирую ;-)

Дмитрий Замоткин



27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
> [a/b] on:ZeroDivide do:[nil].

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

sdfgh153
Да ну вы чего, а.

[ :a :b |
   ^[a / b] ifError: [^nil]
] value: 1.0 value: nil -> nil

Или типа без исключений быстрее?

2010/5/27 Dmitry Zamotkin <[hidden email]>:

> ^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый
> короткий и правильный код на ST, гарантирую ;-)
>
> Дмитрий Замоткин
>
>
>
> 27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
>> [a/b] on:ZeroDivide do:[nil].
>
> --
> http://groups.google.ru/group/sugr



--
take care of the brain

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Alex Kogan
In reply to this post by Dmitry Zamotkin
Не во всяком Smalltalk существует isZero.

2010/5/27 Dmitry Zamotkin <[hidden email]>
^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый
короткий и правильный код на ST, гарантирую ;-)

Дмитрий Замоткин



27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
> [a/b] on:ZeroDivide do:[nil].


--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Dennis Schetinin


27 мая 2010 г. 21:22 пользователь Alex Kogan <[hidden email]> написал:
Не во всяком Smalltalk существует isZero.

Но во всяком его можно сделать.

+1 за использование #ifError: :)
 
2010/5/27 Dmitry Zamotkin <[hidden email]>
^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый

короткий и правильный код на ST, гарантирую ;-)

Дмитрий Замоткин



27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
> [a/b] on:ZeroDivide do:[nil].




--
Dennis Schetinin

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Alex Kogan
Несомненно, но зачем изобретать велосипед, не проще ли:
^ (a isNil or: [ b isNil or: [ b = 0 ]]) ifFalse: [ a/b ]

А вот ловля подобных вещей исключениями - подход не очень правильный, поскольку ловиться будет все подряд и возможно спрячет некие скрытые проблемы кода, которые лучше выявить сразу. Так что выше/ниже приведенная вариация, наиболее строго соответсвует задаче ловить a = nil, b = nil, b= 0, а вот в других случаях пускай себе вылезают исключения, если конечно не ставиться задача делить что хочешь на что хочешь и иногда получать результат.


2010/5/27 Dennis Schetinin <[hidden email]>


27 мая 2010 г. 21:22 пользователь Alex Kogan <[hidden email]> написал:

Не во всяком Smalltalk существует isZero.

Но во всяком его можно сделать.

+1 за использование #ifError: :)
 
2010/5/27 Dmitry Zamotkin <[hidden email]>
^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый

короткий и правильный код на ST, гарантирую ;-)

Дмитрий Замоткин



27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
> [a/b] on:ZeroDivide do:[nil].




--
Dennis Schetinin

--

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Dennis Schetinin
Если уж на то пошло, вообще задача надуманная. Использовать nil-ы в качестве индикаторов "неудачности" выполнения операции — необъектно как-то... Но какой вопрос, такой ответ — я все равно за тот вариант :)

А самое объектное решение было бы в Self-е, если я правльно понимаю? И не нужен паттерн матчинг. Кстати, его можно было бы здесь применить? Для Squeak-а есть такой пэкедж от Лукаса, если не ошибаюсь.

27 мая 2010 г. 21:42 пользователь Alex Kogan <[hidden email]> написал:
Несомненно, но зачем изобретать велосипед, не проще ли:
^ (a isNil or: [ b isNil or: [ b = 0 ]]) ifFalse: [ a/b ]

А вот ловля подобных вещей исключениями - подход не очень правильный, поскольку ловиться будет все подряд и возможно спрячет некие скрытые проблемы кода, которые лучше выявить сразу. Так что выше/ниже приведенная вариация, наиболее строго соответсвует задаче ловить a = nil, b = nil, b= 0, а вот в других случаях пускай себе вылезают исключения, если конечно не ставиться задача делить что хочешь на что хочешь и иногда получать результат.


2010/5/27 Dennis Schetinin <[hidden email]>


27 мая 2010 г. 21:22 пользователь Alex Kogan <[hidden email]> написал:

Не во всяком Smalltalk существует isZero.

Но во всяком его можно сделать.

+1 за использование #ifError: :)
 
2010/5/27 Dmitry Zamotkin <[hidden email]>
^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый

короткий и правильный код на ST, гарантирую ;-)

Дмитрий Замоткин



27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
> [a/b] on:ZeroDivide do:[nil].




--
Dennis Schetinin

--



--
Dennis Schetinin

--
http://groups.google.ru/group/sugr
Reply | Threaded
Open this post in threaded view
|

Re: Защищенное деление

Dmitry Zamotkin
In reply to this post by sdfgh153
Да, исключения достаточно накладны. И здесь видимо тот случай, когда
не грех использовать пусть более длинный, нежели с использованием
#ifError:, но намного более эффективный код.

Дмитрий Замоткин



27 мая 2010 г. 21:21 пользователь Semka Novikov <[hidden email]> написал:

> Да ну вы чего, а.
>
> [ :a :b |
>   ^[a / b] ifError: [^nil]
> ] value: 1.0 value: nil -> nil
>
> Или типа без исключений быстрее?
>
> 2010/5/27 Dmitry Zamotkin <[hidden email]>:
>> ^ (a isNil or: [ b isNil or: [ b isZero ]]) ifFalse: [ a/b ] - самый
>> короткий и правильный код на ST, гарантирую ;-)
>>
>> Дмитрий Замоткин
>>
>>
>>
>> 27 мая 2010 г. 19:08 пользователь Assargadon <[hidden email]> написал:
>>> [a/b] on:ZeroDivide do:[nil].
>>
>> --
>> http://groups.google.ru/group/sugr
>
>
>
> --
> take care of the brain
>
> --
> http://groups.google.ru/group/sugr

--
http://groups.google.ru/group/sugr