NAME
Struct::Dumb - 创建轻量级记录式结构
SYNOPSIS
use Struct::Dumb;
struct Point => [qw( x y )];
my $point = Point(10, 20);
printf "坐标为 (%d, %d)\n", $point->x, $point->y;
$point->y = 30;
printf "新坐标为 (%d, %d)\n", $point->x, $point->y;
struct Point3D => [qw( x y z )], named_constructor => 1;
my $point3d = Point3D( z => 12, x => 100, y => 50 );
printf "Point3D的高度为 %d\n", $point3d->z;
struct Point3D => [qw( x y z )], predicate => "is_Point3D";
my $point3d = Point3D( 1, 2, 3 );
printf "这是一个Point3D\n" if is_Point3D( $point3d );
use Struct::Dumb qw( -named_constructors )
struct Point3D => [qw( x y z )];
my $point3d = Point3D( x => 100, z => 12, y => 50 );
DESCRIPTION
Struct::Dumb 创建类似记录的结构类型,类似于 C、C++ 或 C# 中的 struct 关键字,或 Pascal 中的 Record。调用此模块将创建一个构造函数,返回带有给定字段值的新对象引用。这些引用都支持访问或修改存储值的左值方法。
它特意设计为非对象类。你不能继承它。你不能添加额外的方法。你不能应用角色、混入、元类、特性或其他任何本周流行的概念。
另一方面,它非常小巧,创建轻量级的基于数组的结构,仅使用核心功能。它旨在提供一种更优雅的方式来存储数据结构,避免滥用哈希的风险,例如键名拼写错误。如果传递的参数数量错误,构造函数会报错,同样,引用不存在的字段也会报错。访问器-修改器在带参数调用时会报错。(这有助于检测潜在的错误,例如意外将新值作为参数传递,或尝试通过直接向访问器传递参数来调用存储的 CODE 引用。)
$ perl -E 'use Struct::Dumb; struct Point => [qw( x y )]; Point(30)'
用法: main::Point($x, $y) at -e line 1
$ perl -E 'use Struct::Dumb; struct Point => [qw( x y )]; Point(10,20)->z'
main::Point 没有 'z' 字段 at -e line 1
$ perl -E 'use Struct::Dumb; struct Point => [qw( x y )]; Point(1,2)->x(3)'
main::Point->x 调用时带有参数 at -e line 1.
此类的对象(目前)由 ARRAY 引用支持,但这是内部实现细节,不应通过代码依赖。尝试将对象作为 ARRAY 解引用会抛出异常。
CONSTRUCTOR FORMS
struct 和 readonly_struct 声明根据 named_constructor 选项的设置创建两种不同的构造函数。当为假时,构造函数按字段声明的顺序接受位置值。当为真时,构造函数接受无序的键/值对列表,给出每个命名字段的值。
此选项可以指定给 struct 和 readonly_struct 函数。默认为假,但可以通过在 use 语句中提供 -named_constructors 选项来设置为默认真。
使用命名构造函数时,可以将个别字段声明为可选。通过在字段名前加上 ? 字符,构造函数不会抱怨未提供该字段的命名参数;而是将其设置为 undef。
struct Person => [qw( name age ?address )],
named_constructor => 1;
my $bob = Person( name => "Bob", age => 20 );
# 这是有效的,因为 'address' 被标记为可选
FUNCTIONS
struct
struct $name => [ @fieldnames ],
named_constructor => (1|0),
predicate => "is_$name";
创建一个新的结构类型。这将导出类型名称的新函数到调用者的命名空间。调用此函数返回一个新实例,该实例实现这些字段名的访问器和修改器。
接受以下选项:
-
named_constructor => BOOL
确定结构是否接受位置参数或命名参数。 -
predicate => STR
如果定义,给出要导出到调用者命名空间的第二个函数的名称。此函数将是一个类型测试谓词;即,接受单个参数,当且仅当该参数是此结构类型的实例时返回真。
readonly_struct
readonly_struct $name => [ @fieldnames ],
...
类似于 struct,但此类型的实例在构造后是不可变的。字段访问器方法不会标记为 :lvalue 属性。
接受与 struct 相同的选项。
DATA::DUMP FILTER
自版本 0.10 起。
如果加载了 Data::Dump,将应用一个额外的过滤器,以便以匹配构造它们的格式打印结构实例。
struct Colour => [qw( red green blue )];
use Data::Dump;
my %hash = ( col => Colour( 0.8, 0.5, 0.2 ) );
Data::Dump::dd \%hash;
# 输出 {col => main::Colour(0.8, 0.5, 0.2)}
NOTES
允许 ARRAY 解引用
禁止将实例作为 ARRAY 引用访问的方式目前是通过生成的结构类上的一个内部方法 _forbid_arrayification 实现的。如果特殊情况需要绕过此异常机制,可以用空的 sub {} 主体重载该方法,允许该类的结构实例像普通 ARRAY 引用一样访问。为了良好的实践,应通过局部重载来限制这一点。
例如,Devel::Cycle 需要将实例作为普通 ARRAY 引用访问,以便遍历数据结构查找引用循环。
use Devel::Cycle;
{
no warnings 'redefine';
local *Point::_forbid_arrayification = sub {};
memory_cycle_ok( $point );
}
TODO
- 考虑添加
coerce_hash选项,提供另一个函数将结构转换为键/值对或 HASH 引用。
AUTHOR
Paul Evans leonerd@leonerd.org.uk