zoukankan      html  css  js  c++  java
  • Mono源码学习笔记:Console类(三)

    Buffer 类 (public static class)

    以下就是 mcs/class/corlib/System/Buffer.cs:

    001:  //
    002:  // System.Buffer.cs
    003:  //
    004:  // Authors:
    005:  //   Paolo Molaro (lupus@ximian.com)
    006:  //   Dan Lewis (dihlewis@yahoo.co.uk)
    007:  //
    008:  // (C) 2001 Ximian, Inc.  http://www.ximian.com
    009:  //
    010:  
    011:  //
    012:  // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
    013:  //
    014:  // Permission is hereby granted, free of charge, to any person obtaining
    015:  // a copy of this software and associated documentation files (the
    016:  // "Software"), to deal in the Software without restriction, including
    017:  // without limitation the rights to use, copy, modify, merge, publish,
    018:  // distribute, sublicense, and/or sell copies of the Software, and to
    019:  // permit persons to whom the Software is furnished to do so, subject to
    020:  // the following conditions:
    021:  // 
    022:  // The above copyright notice and this permission notice shall be
    023:  // included in all copies or substantial portions of the Software.
    024:  // 
    025:  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
    026:  // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
    027:  // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
    028:  // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
    029:  // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
    030:  // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
    031:  // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
    032:  //
    033:  
    034:  using System.Runtime.CompilerServices;
    035:  using System.Runtime.InteropServices;
    036:  
    037:  namespace System {
    038:      [ComVisible (true)]
    039:      public static class Buffer {
    040:  
    041:          public static int ByteLength (Array array)
    042:          {
    043:              // note: the other methods in this class also use ByteLength to test for
    044:              // null and non-primitive arguments as a side-effect.
    045:  
    046:              if (array == null)
    047:                  throw new ArgumentNullException ("array");
    048:  
    049:              int length = ByteLengthInternal (array);
    050:              if (length < 0)
    051:                  throw new ArgumentException (Locale.GetText ("Object must be an array of primitives."));
    052:  
    053:              return length;
    054:          }
    055:  
    056:          public static byte GetByte (Array array, int index)
    057:          {
    058:              if (index < 0 || index >= ByteLength (array))
    059:                  throw new ArgumentOutOfRangeException ("index", Locale.GetText(
    060:                      "Value must be non-negative and less than the size of the collection."));
    061:  
    062:              return GetByteInternal (array, index);
    063:          }
    064:  
    065:          public static void SetByte (Array array, int index, byte value)
    066:          {
    067:              if (index < 0 || index >= ByteLength (array))
    068:                  throw new ArgumentOutOfRangeException ("index", Locale.GetText(
    069:                      "Value must be non-negative and less than the size of the collection."));
    070:  
    071:              SetByteInternal (array, index, value);
    072:          }
    073:  
    074:          public static void BlockCopy (Array src, int srcOffset, Array dst, int dstOffset, int count)
    075:          {
    076:              if (src == null)
    077:                  throw new ArgumentNullException ("src");
    078:  
    079:              if (dst == null)
    080:                  throw new ArgumentNullException ("dst");
    081:  
    082:              if (srcOffset < 0)
    083:                  throw new ArgumentOutOfRangeException ("srcOffset", Locale.GetText(
    084:                      "Non-negative number required."));
    085:  
    086:              if (dstOffset < 0)
    087:                  throw new ArgumentOutOfRangeException ("dstOffset", Locale.GetText (
    088:                      "Non-negative number required."));
    089:  
    090:              if (count < 0)
    091:                  throw new ArgumentOutOfRangeException ("count", Locale.GetText (
    092:                      "Non-negative number required."));
    093:  
    094:              // We do the checks in unmanaged code for performance reasons
    095:              bool res = BlockCopyInternal (src, srcOffset, dst, dstOffset, count);
    096:              if (!res) {
    097:                  // watch for integer overflow
    098:                  if ((srcOffset > ByteLength (src) - count) || (dstOffset > ByteLength (dst) - count))
    099:                      throw new ArgumentException (Locale.GetText (
    100:                          "Offset and length were out of bounds for the array or count is greater than " + 
    101:                          "the number of elements from index to the end of the source collection."));
    102:              }
    103:          }
    104:  
    105:          // private
    106:          [MethodImplAttribute (MethodImplOptions.InternalCall)]
    107:          private extern static int ByteLengthInternal (Array array);
    108:  
    109:          [MethodImplAttribute (MethodImplOptions.InternalCall)]
    110:          private extern static byte GetByteInternal (Array array, int index);
    111:  
    112:          [MethodImplAttribute (MethodImplOptions.InternalCall)]
    113:          private extern static void SetByteInternal (Array array, int index, int value);
    114:  
    115:          [MethodImplAttribute (MethodImplOptions.InternalCall)]
    116:          internal extern static bool BlockCopyInternal (Array src, int src_offset, Array dest, int dest_offset, int count);
    117:      }
    118:  }

    上述源程序定义了 Buffer 类。

    这是一个公共静态类。用于操作基元类型的数组,数组中的每一个基元类型都被视为一系列字节。它的公共成员仅仅有下面四个公共静态方法,这些方法比 System.Array 类中相似的方法提供更好的性能:

    1. BtyeLength: public static。返回指定数组中的字节数。(41 – 54 行)
    2. GetByte: public static,在指定数组中检索指定位置处的字节。(56 – 63 行)
    3. SetByte: public static,将指定的值分配给指定数组中特定位置处的字节。(65 – 72 行)
    4. BlockCopy: public static,将指定数目的字节从起始于特定偏移量的源数组拷贝到起始于特定偏移量的目标数组。(74 – 103 行)

    上述四个方法不过在作一些必要的參数检查后调用下述四个非公共的外部静态方法:

    1. ByteLengthInternal: private extern static (106 – 107 行)
    2. GetByteInternal: private extern static (109 – 110 行)
    3. SetByteInternal: private extern static (112 –114 行)
    4. BlockCopyInternalinternal extern static (115 – 116 行)

    上述四个方法都被标记为 [MethodImpl(MethodImplOptions.InternalCall)],也就是说。这四个方法都是对在公共语言执行时本身内部实现的方法的调用。

    请注意 BlockCopyInternal 方法是 internal 的,而不象其它三个方法那样是 private 的。实际上。在 Console.dll 项目中,BlockCopyInternal 方法在 TermInfoReader.cs 中被调用。

    而 Buffer 类的四个公共方法在 Console.dll 项目中都没有被调用。

    IConsoleDriver 接口 (internal interface)

    以下就是 mcs/class/corlib/System/IConsoleDriver.cs:

    01:  //
    02:  // System.IConsoleDriver
    03:  //
    04:  // Author:
    05:  //    Gonzalo Paniagua Javier (gonzalo@ximian.com)
    06:  //
    07:  // (C) 2005 Novell, Inc. (http://www.novell.com)
    08:  //
    09:  
    10:  // Permission is hereby granted, free of charge, to any person obtaining
    11:  // a copy of this software and associated documentation files (the
    12:  // "Software"), to deal in the Software without restriction, including
    13:  // without limitation the rights to use, copy, modify, merge, publish,
    14:  // distribute, sublicense, and/or sell copies of the Software, and to
    15:  // permit persons to whom the Software is furnished to do so, subject to
    16:  // the following conditions:
    17:  // 
    18:  // The above copyright notice and this permission notice shall be
    19:  // included in all copies or substantial portions of the Software.
    20:  // 
    21:  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
    22:  // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
    23:  // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
    24:  // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
    25:  // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
    26:  // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
    27:  // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
    28:  //
    29:  namespace System {
    30:      interface IConsoleDriver {
    31:          ConsoleColor BackgroundColor { get; set; }
    32:          int BufferHeight { get; set; }
    33:          int BufferWidth { get; set; }
    34:          bool CapsLock { get; }
    35:          int CursorLeft { get; set; } 
    36:          int CursorSize { get; set; } 
    37:          int CursorTop { get; set; }
    38:          bool CursorVisible { get; set; }
    39:          ConsoleColor ForegroundColor { get; set; }
    40:          bool KeyAvailable { get; }
    41:          bool Initialized { get; }
    42:          int LargestWindowHeight { get; }
    43:          int LargestWindowWidth { get; }
    44:          bool NumberLock { get; }
    45:          string Title { get; set; }
    46:          bool TreatControlCAsInput { get; set; } 
    47:          int WindowHeight { get; set; }
    48:          int WindowLeft { get; set; }
    49:          int WindowTop { get; set; }
    50:          int WindowWidth { get; set; }
    51:  
    52:          void Init ();
    53:          void Beep (int frequency, int duration);
    54:          void Clear ();
    55:          void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight,
    56:                      int targetLeft, int targetTop, Char sourceChar,
    57:                      ConsoleColor sourceForeColor, ConsoleColor sourceBackColor);
    58:  
    59:          ConsoleKeyInfo ReadKey (bool intercept);
    60:          void ResetColor ();
    61:          void SetBufferSize (int width, int height);
    62:          void SetCursorPosition (int left, int top);
    63:          void SetWindowPosition (int left, int top);
    64:          void SetWindowSize (int width, int height);
    65:          string ReadLine ();
    66:      }
    67:  }

    上述源程序定义了 IConsoleDriver 接口。

    上述源程序第 30 行没有明白指出訪问修饰符。那么这个接口默觉得 internal 的,仅仅能在本程序集中使用。IConsoleDriver 接口是我在这个系列学习笔记第一篇的末尾指出的六个最核心的类型之中的一个,它规定了全部的控制台都必须实现的基本功能。

    IConsoleDriver 共定义了 11 个方法。20 个属性,当中 6 个是仅仅读属性。

    NullConsoleDriver 类 (internal class)

    以下就是 mcs/class/corlib/System/NullConsoleDriver.cs:

    001:  //
    002:  // System.NullConsoleDriver
    003:  //
    004:  // Author:
    005:  //    Gonzalo Paniagua Javier (gonzalo@ximian.com)
    006:  //
    007:  // (C) 2006 Novell, Inc. (http://www.novell.com)
    008:  //
    009:  
    010:  // Permission is hereby granted, free of charge, to any person obtaining
    011:  // a copy of this software and associated documentation files (the
    012:  // "Software"), to deal in the Software without restriction, including
    013:  // without limitation the rights to use, copy, modify, merge, publish,
    014:  // distribute, sublicense, and/or sell copies of the Software, and to
    015:  // permit persons to whom the Software is furnished to do so, subject to
    016:  // the following conditions:
    017:  // 
    018:  // The above copyright notice and this permission notice shall be
    019:  // included in all copies or substantial portions of the Software.
    020:  // 
    021:  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
    022:  // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
    023:  // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
    024:  // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
    025:  // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
    026:  // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
    027:  // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
    028:  //
    029:  #if !NET_2_1
    030:  using System.Runtime.InteropServices;
    031:  using System.Text;
    032:  namespace System {
    033:      class NullConsoleDriver : IConsoleDriver {
    034:          public ConsoleColor BackgroundColor {
    035:              get { return ConsoleColor.Black; }
    036:              set {
    037:              }
    038:          }
    039:  
    040:          public int BufferHeight {
    041:              get { return 0; }
    042:              set {}
    043:          }
    044:  
    045:          public int BufferWidth {
    046:              get { return 0; }
    047:              set {}
    048:          }
    049:  
    050:          public bool CapsLock {
    051:              get { return false; }
    052:          }
    053:  
    054:          public int CursorLeft {
    055:              get { return 0; }
    056:              set {}
    057:          }
    058:  
    059:          public int CursorSize {
    060:              get { return 0; }
    061:              set { }
    062:          }
    063:  
    064:          public int CursorTop {
    065:              get { return 0; }
    066:              set {}
    067:          }
    068:  
    069:          public bool CursorVisible {
    070:              get { return false; }
    071:              set {}
    072:          }
    073:  
    074:          public ConsoleColor ForegroundColor {
    075:              get { return ConsoleColor.Black; }
    076:              set {}
    077:          }
    078:  
    079:          public bool KeyAvailable {
    080:              get { return false; } // FIXME: throw?
    081:          }
    082:  
    083:          public bool Initialized {
    084:              get { return true; }
    085:          }
    086:  
    087:          public int LargestWindowHeight {
    088:              get { return 0; }
    089:          }
    090:  
    091:          public int LargestWindowWidth {
    092:              get { return 0; }
    093:          }
    094:  
    095:          public bool NumberLock {
    096:              get { return false; }
    097:          }
    098:  
    099:          public string Title {
    100:              get { return ""; }
    101:              set {}
    102:          }
    103:  
    104:          public bool TreatControlCAsInput {
    105:              get { return false; }
    106:              set {}
    107:          }
    108:  
    109:          public int WindowHeight {
    110:              get { return 0; }
    111:              set {}
    112:          }
    113:  
    114:          public int WindowLeft {
    115:              get { return 0; }
    116:              set {}
    117:          }
    118:  
    119:          public int WindowTop {
    120:              get { return 0; }
    121:              set {}
    122:          }
    123:  
    124:          public int WindowWidth {
    125:              get { return 0; }
    126:              set {}
    127:          }
    128:  
    129:          public void Beep (int frequency, int duration)
    130:          {
    131:          }
    132:  
    133:          public void Clear ()
    134:          {
    135:          }
    136:  
    137:          public void MoveBufferArea (int sourceLeft, int sourceTop, int sourceWidth, int sourceHeight,
    138:                      int targetLeft, int targetTop, Char sourceChar,
    139:                      ConsoleColor sourceForeColor, ConsoleColor sourceBackColor)
    140:          {
    141:          }
    142:  
    143:          public void Init ()
    144:          {
    145:          }
    146:  
    147:          public string ReadLine ()
    148:          {
    149:              return null;
    150:          }
    151:  
    152:          public ConsoleKeyInfo ReadKey (bool intercept)
    153:          {
    154:              return ConsoleKeyInfo.Empty;
    155:          }
    156:  
    157:          public void ResetColor ()
    158:          {
    159:          }
    160:  
    161:          public void SetBufferSize (int width, int height)
    162:          {
    163:          }
    164:  
    165:          public void SetCursorPosition (int left, int top)
    166:          {
    167:          }
    168:  
    169:          public void SetWindowPosition (int left, int top)
    170:          {
    171:          }
    172:  
    173:          public void SetWindowSize (int width, int height)
    174:          {
    175:          }
    176:      }
    177:  }
    178:  #endif

    上述源程序定义了 NullConsoleDriver 类。整个源程序(除了开头的凝视以外)被第 29 行的“#if !NET_2_1” 和第 178 行的“#endif”预处理指令括了起来,表明该类不能用在 Moonlight 中,实际上 Moonlight 是应用于 Web 的,不须要控制台的概念。

    这里的 NET_2_1 表示 .NET 2.1。而 Moonlight 是基于 .NET 2.1 的,详细请參见:MoonlightNotes

    从上述源程序能够看出,该类的全部成员都是 public 的。并且刚好有 31 个成员,不过满足 IConsoleDriver 接口的要求。

    第 34 行到第 127 行是 20 个属性,这些属性的 set 方法(假设不是只读属性的话)都是空的,get 方法也不过返回空字符串、零、null、false、true、或者 ConsoleColor.Black。

    第 129 行到第 176 行是 11 个方法,这些方法或者是空的,或者只返回 null 或者 ConsoleKeyInfo.Empty。

    NullConsoleDriver 类实践了 Null Object 设计模式。

    在 Console.dll 项目中,NullConsoleDriver 类仅在 ConsoleDriver.cs 中被使用过一次。

  • 相关阅读:
    Delphi 实现C语言函数调用
    Delphi采用接口实现DLL调用
    select、poll、epoll之间的区别总结[整理]
    int 的重载
    qt 安装包生成2
    线程池的简单实现
    qt 安装包生成
    linux 下tftpf搭建
    2018C语言助教总结
    动态规划——最长子序列长度
  • 原文地址:https://www.cnblogs.com/llguanli/p/6784855.html
Copyright © 2011-2022 走看看