如何在Hacklang中定义空dict <string,int =“”>

时间:2018-09-19 22:08:19

标签: hacklang

我的形状如下:

const type A = shape(
  'b' => dict<string, int>,
);

如何用空字典创建此形状?例如从此功能

function getA(): A {
  return shape(
    'b' => ???
  );
}

2 个答案:

答案 0 :(得分:4)

不知道我使用了什么语言功能,但这可以解决问题。

function getA(): A {
  return shape(
    'b' => dict[]
  );
}

如果有人有更多背景信息,请添加您的答案,我会接受

答案 1 :(得分:1)

  

这是Hack阵列建议的一部分

     

dict数组是将有效arraykey映射到值的容器。这个   反映Map类的行为。这将是一个数组   具有额外限制的运行时,使其可以像   从类型检查器角度进行映射。这主要集中在   所需的运行时行为,但如果对其运行方式有疑问   与类型检查器进行交互,我将很乐意讨论。文字   构造函数

     

使用文字表达式dict []构造dict。

$dict = dict[]; // Empty dict-array
$dict = dict['a' => 1, 'b' => 2, 'c' => 3]; // dict-array of 3 elements
     

这是一个静态表达式,因此可以在静态中使用   初始化程序。

class C {
  public static dict<string, int> $dict = dict[
    'a' => 1,
    'b' => 2,
    'c' => 3,
  ];
}
     

源:https://github.com/facebook/hhvm/issues/6452

创建字典(dict[]或向量(vec[])时无需定义类型,因为在运行时会忽略泛型

示例:

function spamMessages(dict<string, string> $messages): void
{
    foreach($messages as $user => $message) {
        echo $user . ': ' . $message;
    }
}

function listUsers(vec<string> $users): void
{
    foreach($users as $user) {
        echo '-' . $user;
    }
}

$messages = dict[
    'azjezz' => 'bring the cookies'
];

$users = vec[
    'azjezz'
];

spamMessages($messages);
listUsers($users);

在此示例中,类型检查器足够聪明,可以看到$message同时具有类型为string的键和值,因此不会引发任何错误。

您还可以使用vecdict帮助器

从php样式的数组创建dict数组或向量

$array = [
    'a' => 1,
    'b' => 'c'
];

$dict = dict($array);

在上面的示例中,类型检查器知道$array中键的类型,并且由于dict助手被声明为dict<Tk, Tv>(array<Tk, Tv> $array): dict<Tk, Tv>,因此它知道返回的字典数组包含键和值的类型相同。

有时您可能无法告知类型检查器数组键和值的类型。

示例:

$array = json_decode('path/to/file.json');

您知道json文件包含例如字符串键和值的数组,但是在这里类型检查器认为$array的类型为mixed,因为无法真正分辨出文件中的内容

为了克服这一点,您可以使用as运算符告诉类型检查器有关$array类型的信息

$array = json_decode('path/to/file.json') as array<_, _>;

请注意,这里我们使用_而不是string,并且它们键入检查器将假设$array现在是array<arraykey, mixed>类型,原因是不支持泛型截至目前,使用as运算符,但是将来可能会更改,因此我们可以进行as array<string, string>

之后,您可以根据该数组创建字典:

$dict = dict($array);

例如,如果您知道该文件无法在字符串键和值旁边包含任何内容,并且想要强制该类型,则可以使用以下帮助程序将其强制转换为dict<string, string>类型的字典,但是我不推荐这样做,因为在将non-stringable对象或资源转换为字符串时可能会导致错误。

// KeyedContainer = array, dict, maps and other keyed containers 
function forceStringDict(KeyedContainer<arraykey, mixed> $container): dict<string, string>
{
    $dict = dict[];
    foreach($container as $k => $v) {
        $dict[(string) $k] = (string) $v;
    }
    return $dict;
}

$dict = forceStringDict($dict);