关于c#:有趣的OOPS难题

Interesting OOPS puzzle

最近,我在一次采访中遇到了以下问题。起初我认为这个问题是错误的,但面试官提到了解决这个问题的办法。对于此类:

1
2
3
4
5
6
7
public class BaseHome
{
    public static void Main()
    {
        Console.WriteLine("A");
    }
}

将以下内容写入控制台:

1
2
3
B
A
C

规则:

  • 不要更改主功能。
  • 不要创建任何附加类。
  • 怎么能做到?


    假设您的意思是三行的b a c(加上main方法名上没有拼写错误):

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    namespace ConsoleApplication1
    {
        public class BaseHome
        {
            static BaseHome()
            {
                Console.WriteLine("B");

                AppDomain.CurrentDomain.ProcessExit += new EventHandler(OnProcessExit);
            }

            public static void Main()
            {
                Console.WriteLine("A");
            }

            private static void OnProcessExit(object sender, EventArgs e)
            {
                Console.WriteLine("C");
                Console.Read();
            }
        }
    }


    哈哈哈,我知道了。创建静态属性!

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    public class BaseHome
    {
        public static void Main()
        {
           Console.WriteLine("A");
        }

        public static BaseHome Console
        {
            get{ return new BaseHome(); }
        }

        public void WriteLine(string s) {
            System.Console.WriteLine("BCA"); //Or multiple lines if you like
        }

    }

    编辑:或者,对,只是一个字段

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    public class BaseHome
    {
        static BaseHome Console = new BaseHome();

        public static void Main()
        {
           Console.WriteLine("A");
        }

        public void WriteLine(string s) {
            System.Console.WriteLine("BCA"); //Or multiple lines if you like
        }

    }


    没有新类型。没有显式创建对象。在真正的控制台应用程序中工作。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    public class BaseHome
    {
        static System.IO.TextWriter Console
        {
            get
            {
                System.Console.Write("  C
    B"
    );
                return System.Console.Out;
            }
        }
        public static void Main()
        {
            Console.WriteLine("A");
            // System.Console.ReadLine();
        }
    }

    结果是BAC—在同一行上不少于!

    (通过使用CurstorLeft/Top或直接转义序列,可以根据后期编辑调整为多行输出。)

    说明:

    静态属性(Console被解析,而不是Console.WriteLine("A")中的类型,因为属性隐藏了这里的类型;这就是为什么System.Console被用来引用控制台类本身的原因。

    console get属性导致写入控制台的副作用-它写入"uu c",然后使用cr(回车)来"返回到行开始"并写入"b",因此行是"b_c",将光标留在"b"之后。

    然后,该属性返回与具有writeline的控制台关联的TextWriter。然后调用textwriter的writeline,而不是控制台的静态writeline,并写入字符"a"(在"b"之后),因此结果是"bac"。

    这利用了上下文特定的行为,因为它是一个控制台,能够理解如何移动光标(例如使用"
    "或其他光标定位)。


    只需要一个静态构造函数:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    public class BaseHome
    {
        static BaseHome()
        {
            Console.WriteLine("B
    A
    C"
    );
            Console.SetOut(System.IO.TextWriter.Null);
        }

        public static void Main()
        {
            Console.WriteLine("A");
        }
    }

    与重定向输出流不同,其他选项包括调用Environment.Exit、抛出未处理的异常或永远旋转。目前尚不清楚该计划是否需要正常终止(或完全终止)。


    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    struct ConsoleStruct
    {
        private string _text;
        public ConsoleStruct(string text)
        {
            _text = text;
        }

        public void WriteLine(string txt)
        {
            Console.WriteLine(_text);
        }
    }
    class Program
    {
        private static ConsoleStruct Console = new ConsoleStruct("B A C");
        static void Main(string[] args)
        {
            Console.WriteLine("A");
        }
    }