在 F# 中测试空引用 [英] Testing for null reference in F#

查看:15
本文介绍了在 F# 中测试空引用的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

鉴于以下内容:

[<DataContract>]
type TweetUser = {
    [<field:DataMember(Name="followers_count")>] Followers:int
    [<field:DataMember(Name="screen_name")>] Name:string
    [<field:DataMember(Name="id_str")>] Id:int
    [<field:DataMember(Name="location")>] Location:string}

[<DataContract>]
type Tweet = {
    [<field:DataMember(Name="id_str")>] Id:string
    [<field:DataMember(Name="text")>] Text:string
    [<field:DataMember(Name="retweeted")>] IsRetweeted:bool
    [<field:DataMember(Name="created_at")>] DateStr:string
    [<field:DataMember(Name="user", IsRequired=false)>] User:TweetUser
    [<field:DataMember(Name="sender", IsRequired=false)>] Sender:TweetUser
    [<field:DataMember(Name="source")>] Source:string}

使用 DataContractJsonSerializer(typeof<Tweet[]>) 进行反序列化将导致 User 或 Sender 字段为空(至少调试器告诉我的是).

Deserializing with DataContractJsonSerializer(typeof<Tweet[]>) will result in either the User or Sender field being null (at least that's what the debugger is telling me).

如果我尝试编写以下内容:

If I try to write the following:

    let name = if tweet.User <> null 
                  then tweet.User.Name
                  else tweet.Sender.Name

编译器发出错误:'TweetUser'类型没有'null'作为正确值"

the compiler emits the error: "The type 'TweetUser' does not have 'null' as a proper value"

在这种情况下如何测试空值?

How do I test null values in this case?

推荐答案

循环扩展@Tomas 的回答 ;-]

To cyclically expand on @Tomas' answer ;-]

let name = if not <| obj.ReferenceEquals (tweet.User, null)
              then tweet.User.Name
              else tweet.Sender.Name

let inline isNull (x:^T when ^T : not struct) = obj.ReferenceEquals (x, null)

Unchecked.defaultof<_> 正在做正确的事情并为您的记录类型生成空值;问题是默认的相等运算符使用通用结构比较,它希望您在使用 F# 类型时始终遵守 F# 的规则.在任何情况下,空检查实际上只保证首先进行引用比较.

Unchecked.defaultof<_> is doing the right thing and producing nulls for your record types; the issue is that the default equality operator uses generic structural comparison, which expects you to always play by F#'s rules when using F# types. In any case, a null-check really only warrants referential comparison in the first place.

这篇关于在 F# 中测试空引用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆