代码之家  ›  专栏  ›  技术社区  ›  Peter Booster

在运行时更改内部表示

  •  1
  • Peter Booster  · 技术社区  · 16 年前

    更新 主要问题仍然是 在这个例子下,但我想它可以归结为 致:

    快速、强大的类型,一次仅占1% 非常重的类型(比如int vs。 BigInteger)如何表示它**

    在一所学校里,我们学到了很多关于内部表示的知识,但从未学会如何在运行时更改它。我的意思是:假设你有一个代表小数点的类,但你用一个整数来表示它的内部,直到你实际需要一个比整数大的值,并且只比改变表示法。。。

    interface INumber
        {
            void add1000();
            void SetValue(decimal d);
            decimal GetValue();                     
        } 
    

    我发现这两种实现中的后一种在很多情况下都更强大,包括 this one

        1. Representation by only a decimal
    
            public class Number1:INumber
            {
    
                private decimal d { get; set; }
    
    
                public void add1000()
                {
                    d += 1000;
                }
    
    
    
                public decimal GetValue()
                {
                    return d;
                }
    
    
    
                public void SetValue(decimal d)
                {
                    this.d = d;
                }
    
            }
    
    
    2. Representation by a decimal and an int
    
    public class Number2:INumber
        {
            private bool usedecimal; 
            private int i;
            private decimal d;
    
            public void add1000()
            {
                if (usedecimal)
                {
                    d += 1000;
                    return; 
                }
    
                i += 1000;
    
                if (i > 2147480000)
                {
                    d = i;              
                    usedecimal = true;              
                }
    
    
            }
    
            public void SetValue(decimal d)
            {
                try
                {
                    i = (int)d;
    
                }
                catch (OverflowException e)
                {
    
                    this.d = d;
                }
    
            }
    
            public decimal GetValue()
            {
                return Math.Max(i,d);
            }
        }
    }
    

    我的问题如下:

    • 是否有混合表示的指南,何时使用,何时不使用?
    • 当混合代表性在没有基准测试的情况下可以更快时,如何有预感?
    • 有什么例子吗?
    2 回复  |  直到 9 年前
        1
  •  8
  •   Eric Lippert    16 年前

    BigInteger实现通常正是这样做的;它们将所有内容保持在整数或长整数中,直到有内容溢出,然后才转到更重的实现。

    有很多种方法可以表示它。我喜欢的一种模式是:

    public abstract class Thing
    {
        private class LightThing : Thing
        { ... }
        private class HeavyThing : Thing 
        { ... }
        public static Thing MakeThing(whatever) 
        { /* make a heavy or light thing, depending */ }
        ... etc ...
    }
    

    当然我们可以很容易地编制这样一份清单。如果满足以下条件,则此技术有意义:

    (2) 通常情况下,轻量级代码路径的使用最多

    (3) 与重量级解决方案的成本相比,检测转换的成本并不重要

    (4) 为了实现以客户为中心的、现实的性能目标,需要更复杂的双表示解决方案。

    当混合代表性在没有基准测试的情况下可以更快时,如何有预感?

    不要。根据直觉做出绩效决策是在事实之前进行推理。推动公司的绩效决策 现实的 以客户为中心 , 数据驱动 分析,而不是凭直觉。如果说这些年来我在绩效分析方面学到了一件事,那就是我的直觉通常是错误的。

    有什么例子吗?

    把我打得要死。我不太喜欢记忆模式分类法。

    见上文。

        2
  •  0
  •   Joel Lucsy    16 年前