代码之家  ›  专栏  ›  技术社区  ›  Alex

C真实和虚假的价值观

  •  27
  • Alex  · 技术社区  · 15 年前

    在JavaScript中,有真实和错误值的概念。

    例如

    • 0:始终为假
    • 1:永远真实
    • “0”:始终为真
    • “1”:始终为真

    在.NET框架的C语言中,是否有一个真实和虚假值的等效列表?

    我之所以想知道这一点,是因为我发现自己在做以下工作

    if(obj != null)
    {
       // Do something with the object
    }
    

    当我能写下以下

    if(obj)
    {
       // Do something with the object
    }
    
    10 回复  |  直到 15 年前
        1
  •  40
  •   Dan Herbert    15 年前

    C只有文字 true false 价值观。

    C要求您在声明中非常明确,因为它是一种强类型语言,而不是在需要时可以进行隐式转换的JavaScript。

    重要的是要注意,“强类型”并不是C不隐式转换为“真实/错误”值的原因。该语言有意避免其他编译语言(如C++)的缺陷,其中某些值可以是真的,比如 0 “或” 1 '这可能会使您犯语法错误,直到运行时,当您的代码出现意外行为时,您可能才注意到这一点。

        2
  •  22
  •   Sir Rippov the Maple    15 年前

    默认情况下,C仅提供 true false .

    但是,通过实现 操作员。当类型实现 运算符,该类型的实例可以用作布尔表达式。从第7.19节 C# Language Specification :

    如果布尔表达式的类型不能隐式转换为bool,但实现了operator true,则在对表达式进行计算之后,将调用该类型提供的operator true实现来生成bool值。

    这个 DBBool _§11.4.2中的结构类型提供了实现operator true和operator false的类型示例。

    下面是 接线员(这可能会完成你想做的事情):

    public static bool operator true(MyType myInstance)
    {
        return myInstance != null;
    }
    

    如果您执行 运算符,则必须实现 接线员。

        3
  •  15
  •   Eric Lippert    15 年前

    您的问题的正确答案见C 3.0规范第7.19节,您可以在互联网上轻松找到。为方便起见,相关文本如下:

    7.19布尔表达式

    布尔表达式是一个表达式 这将产生bool类型的结果。

    控制条件表达式 if语句的[…]是 布尔表达式。[…]

    布尔表达式必须是 可以隐式 转换为bool或 实现运算符true。如果既不 满足要求,a 发生编译时错误。

    当布尔表达式为类型时 无法隐式转换为 bool,但实现operator true, 然后进行评估 表达式,运算符true 由该类型提供的实现 调用以生成bool值。

    除了bool本身之外,没有其他类型可以通过内置转换隐式转换为bool,但当然,用户可以定义到bool的用户定义隐式转换。

        4
  •  13
  •   dtb    15 年前

    简短回答:

    C中:

    • 真的:总是真的
    • 错误:总是错误

    其他一切都不是布尔值。

        5
  •  11
  •   ojrac    15 年前

    这样的代码将(并且应该)无法编译。如果您特别想重写该行为,可以创建一个 implicit conversion 布尔运算。像这样:

    public class Foo {
        public static implicit operator bool(Foo me) {
            if (me == null) {
                return false;
            }
    
            return true; // maybe add more logic before saying True
        }
    }
    

    我认为这是一个糟糕的实践,因为对于一个不熟悉您的项目的编码人员来说,还不清楚是什么逻辑提供了布尔转换。更惯用的方法是通过静态助手函数显式地告诉读者代码在做什么,就像内置的字符串类那样:

    if (String.IsNullOrEmpty(str){
        // ...
    }
    

    代码只写一次,而且经常读;优化可读性。

        6
  •  3
  •   CRice    15 年前

    if语句计算可转换为/等于/返回布尔值或布尔值本身的值…像obj一样检查空值!=null是这样一个表达式,

    只有当obj能够转换为bool时,“if(obj)”才能工作,如果它为空则不工作。

        7
  •  3
  •   Ronnie Overby    10 年前

    前面的答案是正确的。但是,我有一个扩展方法,在一些罕见的情况下使用它:

    public static bool IsTruthy(this object obj)
    {
        if (obj == null || obj is DBNull)
            return false;
    
        var str = obj as string;
        if (str != null)
            return !string.IsNullOrWhiteSpace(str) && 
                !str.Trim().Equals(bool.FalseString, StringComparison.OrdinalIgnoreCase);
    
        try
        {
            if (Convert.ToDecimal(obj) == 0)
                return false;
        }
        catch { }
    
        if (obj is BigInteger)
            return ((BigInteger)obj) != 0; 
    
        return true;
    }
    

    关于这方面的一些注意事项:

    • 此方法与javascript处理字符串“false”的方式不一致。
    • 对于空的可枚举项,此方法返回true,这与javascript一致。
        8
  •  0
  •   Peter Tate    15 年前

    如果 obj 是您创建的类型,可以定义用户定义的隐式转换为 bool .

        9
  •  0
  •   LEMUEL ADANE    6 年前

    你可以通过扩展方法来定义你自己的真实和错误。

    public static bool Falsy(this object obj) {
            if(obj == null) return true;
            if (obj is string)
                if(obj as string == string.Empty) return true;
            if(obj is byte)
                if((byte)obj == 0) return true;
            if(obj is sbyte)
                if((sbyte)obj == 0) return true;
            if(obj is short)
                if((short)obj == 0) return true;
            if(obj is ushort)
                if((ushort)obj == 0) return true;
            if(obj is int)            
                if((int)obj == 0) return true;
            if(obj is uint)
                if((uint)obj == 0) return true;
            if(obj is long)
                if((long)obj == 0) return true;
            if(obj is ulong)
                if((ulong)obj == 0) return true;
            if(obj is float)
                if((float)obj == 0) return true;
            if(obj is double)
                if((double)obj == 0) return true;
            if(obj is decimal)
                if((decimal)obj == 0) return true;
            if(obj is IEnumerable<object>)
                if((obj as IEnumerable<object>).Count<object>() == 0)
                    return true;
            if(obj is Array)
                if(((Array)obj).Length <= 0)
                    return true;
            if(obj is ObjectId)
                if(((ObjectId)obj).Pid == 0) return true;
            if(obj is System.Collections.ObjectModel.ObservableCollection<M>)
                if(((ObservableCollection<M>)obj).Count <= 0) return true;
                    return false;
    }
    
    public static bool Truthy(this object obj) {
       return !Falsy(obj);
    }
    

    所以你可以这样做:

    if(customerList.falsy())引发新异常(“不能为空。”);

        10
  •  -5
  •   MiffTheFox    15 年前

    C是一种静态类型的语言,也就是说,对象的类型在设置它是什么时很重要。

    例如,“4”!= 4。

    然而,JavaScript是一种动态类型化语言,因此类型的重要性很小。

    所以在javascript中,“4”==4。

    “真实”值是恰好满足x==true的值,而“虚假”值则不满足。

    如果没有类型安全,某些特性(如重载)将产生不可预测的行为。

    更多信息,您可以看到 here .