第 4 章 类型设计 类型设计
本作品已使用人工智能进行翻译。欢迎您提供反馈和意见:translation-feedback@oreilly.com
给我看你的流程图,隐藏你的表格,我会继续感到神秘。给我看你的表格,我通常就不需要你的流程图了,它们会很明显。
弗雷德-布鲁克斯,《神话人物月
弗雷德-布鲁克斯(Fred Brooks)引用的 语言已经过时,但其观点仍然正确:如果看不到代码所操作的数据或数据类型,就很难理解代码。这正是类型系统的一大优势:通过写出类型,代码的读者可以看到它们。这样,你的代码就可以理解了。
其他章节介绍了 TypeScript 类型的核心内容:使用它们、推断它们以及使用它们编写声明。本章将讨论类型本身的设计。本章中的示例都是以 TypeScript 为对象编写的,但其中的大多数想法都具有更广泛的适用性。
如果你能很好地编写类型,那么幸运的话,你的流程图也将是显而易见的。
第 28 项:优先选择始终表示有效状态的类型
如果 你能很好地设计你的类型,那么你的代码应该很容易编写。但是,如果类型设计得不好,那么再多的聪明才智或文档也无济于事。你的代码将变得混乱不堪,而且容易出错。
有效类型设计的关键在于设计只能表示有效状态的类型。本节将通过几个示例来说明如何出错,并告诉你如何解决这些问题。
假设您正在构建一个网络应用程序,让您选择一个页面,加载该页面的内容,然后显示它。您可能会这样编写状态:
interfaceState{pageText:string;isLoading:boolean;error?:string;}
在编写渲染页面的代码时,需要考虑所有这些字段:
functionrenderPage(state:State){if(state.error){return`Error! Unable to load${currentPage}:${state.error}`;}elseif(state.isLoading){return`Loading${currentPage}...`;}return`<h1>${currentPage}</h1>\n${state.pageText}`;}
但这样做对吗?如果isLoading 和error 都被设置了呢?这意味着什么?是显示加载信息好,还是显示错误信息好?这很难说!没有足够的信息可用。
或者,如果您正在编写一个changePage 函数呢?下面是一个尝试:
asyncfunctionchangePage(state:State,newPage:string){state.isLoading=true;try{constresponse=awaitfetch(getUrlForPage(newPage));if(!response.ok){thrownewError(`Unable to load${newPage}:${response.statusText}`);}consttext=awaitresponse.text();state.isLoading=false;state.pageText=text;}catch(e){state.error=''+e;}}
这样做有很多问题!这里有几个:
-
在出错的情况下,我们忘记将
state.isLoading设置为false。 -
我们没有清除
state.error ...
Become an O’Reilly member and get unlimited access to this title plus top books and audiobooks from O’Reilly and nearly 200 top publishers, thousands of courses curated by job role, 150+ live events each month,
and much more.
Read now
Unlock full access