如何使我的 Perl 方法更像 Moose?
我正在 Perl 中练习 Kata Nine: Back to the CheckOut 同时也尝试使用第一次见到驼鹿。
到目前为止,我已经创建了以下类:
package Checkout;
# $Id$
#
use strict;
use warnings;
our $VERSION = '0.01';
use Moose;
use Readonly;
Readonly::Scalar our $PRICE_OF_A => 50;
sub price {
my ( $self, $items ) = @_;
if ( defined $items ) {
$self->{price} = 0;
if ( $items eq 'A' ) {
$self->{price} = $PRICE_OF_A;
}
}
return $self->{price};
}
__PACKAGE__->meta->make_immutable;
no Moose;
1;
整个 price
方法感觉不太像 Moose,我觉得这可以进一步重构。
有人对如何改进有任何意见吗?
I am practising Kata Nine: Back to the CheckOut in Perl whilst also trying to use Moose for the first time.
So far, I've created the following class:
package Checkout;
# $Id$
#
use strict;
use warnings;
our $VERSION = '0.01';
use Moose;
use Readonly;
Readonly::Scalar our $PRICE_OF_A => 50;
sub price {
my ( $self, $items ) = @_;
if ( defined $items ) {
$self->{price} = 0;
if ( $items eq 'A' ) {
$self->{price} = $PRICE_OF_A;
}
}
return $self->{price};
}
__PACKAGE__->meta->make_immutable;
no Moose;
1;
The whole price
method doesn't feel very Moose-ish and I feel like this could be refactored further.
Does anyone have any input on how this could be improved?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我注意到的第一件事是您没有为您的
班级。
这违反了使用 Moose 提供的大部分封装。驼鹿解决方案
至少会让
price
成为一个实际的属性。然而,您提供的代码的主要问题是您没有
真正对 Kata 描述的问题进行建模。首先是卡塔
指出您需要在每次调用时传递定价规则
结帐对象。所以我们知道我们需要将这个状态保存在其他东西中
比一系列 ReadOnly 类变量。
您会看到这里的价格方法现在是使用 Moose 的“Native
属性”委托。这将在项目和规则之间执行查找。
然而,这不会处理对不存在的元素进行查找的情况
存在。展望一下 Kata 提供的单元测试之一就是这样的
一种查找:
因此我们需要稍微修改价格方法来处理这种情况。
基本上,我们检查是否有价格规则,否则返回 0。
接下来,我们需要在扫描商品时对其进行跟踪,以便建立总计。
同样,“本机属性”委托提供了
scan
方法,测试中的Kata正在寻找。
最后,使用
List::Util
的sum
函数可以轻松实现total
方法。这段代码并没有完全实现 Kata 的解决方案,但它确实实现了
提出问题状态的更好模型并显示更多
“穆西”解决方案。
完整的代码和翻译的测试如下所示。
First thing I noticed is that you're not using an explicit attribute for your
class.
This violates most of the encapsulation that using Moose provides. A Moose solution
would at the least make
price
into an actual attribute.However the main problem with the code you've presented is that you're not
really modeling the problem described by the Kata. First the Kata specifically
states that you'll need to pass in the pricing rules on each invocation of the
Checkout Object. So we know we'll need to save this state in something other
than a series of ReadOnly class variables.
You'll see the price method here is now a delegate using Moose's "Native
Attributes" delegation. This will perform a lookup between an Item and a Rule.
This however won't handle the case of a lookup on a element that doesn't
exist. Peeking ahead one of the unit tests the Kata provides is exactly that
kind of a lookup:
So we'll need to modify the price method slightly to handle that case.
Basically we check to see if we have a price rule, otherwise we return 0.
Next we'll need to track the items as they're scanned so we can build a total.
Again the "Native Attributes" delegation provides the
scan
method that thetest in the Kata are looking for.
Finally a
total
method is trivial usingList::Util
'ssum
function.This code doesn't fully implement the solution to the Kata, but it does
present a much better model of the problem state and show's a much more
"Moosey" solution.
The full code and translated tests are presented below.
use strict;
和use warnings;
可以删除,因为use Moose;
已经为您做到了这一点。您还可以使用 Moose 创建只读属性,而不是使用Readonly
模块。The
use strict;
anduse warnings;
can be removed asuse Moose;
will already do that for you. You can also use Moose to create read-only attribute instead of usingReadonly
module.