为什么Flow在访问数组元素时会忽略undefined的可能性?

Why does Flow ignore the possibility of undefined when accessing an array element?

这个函数有一个错误。 capitalize('') 会抛出

TypeError: Cannot read property 'toUpperCase' of undefined.

// @flow

function capitalize(str: string) {
  return str[0].toUpperCase() + str.slice(1)
}

这是因为

var a = "foo" // : string
var b = a[0] // also : string

但是为什么流推断 bstring 而不是 string|void 这似乎是 b 的正确类型?

这可以通过类型转换强制执行

return (str[0]: string|void).toUpperCase() + str.slice(1)

来自documentation

Undefined Values and Optional Types

Undefined values, just like null, can cause issues too. Unfortunately, undefined values are ubiquitous in JavaScript and it is hard to avoid them without severely affecting the usability of the language. For example, arrays can have holes for elements; object properties can be dynamically added and removed. Flow ignores the possibility of undefined resulting from object property and array element accesses. Being stricter would force the programmer to do undefined checks (like null checks) on each dereference of an array element or object property to get anything useful done.