C#基础

数据类型

string int double long char byte

可空类型

int? i = 3;

Nullable i = new Nullable(3);

参数数组 params关键字

使用params关键字,在传递参数时,既可以传数组,也可以传数组参数

public int AddElements(params int[] arr)

@在c#中为强制不转义的符号,在里面的转义字符无效。

string的使用及常见方法

string fname,lname;
fname = "Rowan";
lname = "Atkinson";
string fullnamme = fname+lname;
Console.WriteLine("Full Name:{0}", fullname);

char lettes = {'H','e','l','l','o'};
string greetings = new string(lettes);

比较两个string对象,并返回一个表示它们在排列顺序中相对位置的整数,该方法区分大小写
static int Compare(string strA, string strB)
如果不区分大小写
static int Compare(string strA, string strB, bool ignoreCase=true)
连接两个string,返回合并后的内容
static string Concat(string str0, string str1)
有连接三个、四个的重载方法

指定string对象中是否出现在字符串中
bool Contains(string value)

创建一个与指定字符串具有相同值得新的string对象
string Copy(string str)

复制string对象指定位置开始的值到字符数组的指定位置
void CopyTo(int sourceIndex, char[] destination, int destinationIndex,  int count)

//比较字符串是否相等
bool Equals(string value)

//字符串格式化
string Format("",...)

//字符串查找
int indexOf(char value)
int indexOf(string value)

从指定位置查找
int indexOf(char[] value, int startIndex)
int indexOf(string value, int startIndex)
int indexOfAny(char[] anyOf)

返回一个新的字符串,其中,指定的字符串被插入在当前 string 对象的指定索引位置。
int insert(int startIndex, string value)

指示指定的字符串是否为null 或者是否为一个空的字符串
static bool IsNullOrEmpty(string value)

连接一个字符串数组中的所有元素,使用指定的分隔符分隔每个元素
static string Join(string separator, string[] value)
连接 指定位置开始,指定连接数量
static string Join(string separator, string[] value, int startIndex, int count)

//从字符串末尾搜索字符串第一次出现的位置
int LastIndexOf(char value)
int LastIndexOf(string value)

//移除当前实例中的所有字符,从指定位置开始,一直到最后一个位置为止,并返回字符串
string Remove(int startIndex)
string Remove(int startIndex, int count)

//字符串替换
string Replace(char oldChar, char newChar)
string Replace(string oldValue, string newValue)

//字符串分割===========
string[] Split(params char[] separator)
指定最大数量
string[] Split(params char[] separator, int count)

//正则替换

//比较前缀
bool StartWith(string value)

//比较后缀
bool EndsWith(string value)

//传gbk编码
byte[] buffer = Encoding.GetEncoding("GBK").GetBytes(str)
//转utf8编码
byte[] buffer = Encoding.GetEncoding("UTF-8").GetBytes(str)
//转char数组
bool ToCharArray()
bool ToCharArray(int startIndex, int length)

//将字符串转换为小写
string ToLower()
//将字符串转换为大写
string ToUpper()
//去除前导空格和后置空格
string Trim()

常见的类

Array

//逆转数组
Array.Reverse(list)
//排序数组
var list = {34,72,13,44,25,30,10}
Array.Sort(list)

LIst

List ListOfT = new List();

List<Person> persons = new List<Person>();
persons.Add(p1);
persons.Add(p2);
persons.Add(p3);
persons.Remove("name");
persons.Count();
persons.Clear();
persons.RemoveAt(0);

交错数组 int[][] sources;

int [][] scores = new int[5][]; //创建第一维
for(int i=0; i<scores.length;i++){ 
   scores[i] = new int[4]; //遍历创建第二维
}

Hashable

Hashtable table = new Hashtable();
table.Add("name","yingzi");
table.Add("arg","0");
table.Add("datetime","2021-12-24")

table.Remove("name");
table.Clear();
//判断是否存在指定的键
table.Contains("name");

Object

//所有类默认继承Object类,包含Equals GetHashCode ToString Copy
 class Point
    {
        public int x, y;

        public Point(int x, int y)
        {
            this.x = x;
            this.y = y;
        }
        public override bool Equals(object obj)
        {
            // If this and obj do not refer to the same type, then they are not equal.
            if (obj.GetType() != this.GetType()) return false;

            // Return true if  x and y fields match.
            Point other = (Point)obj;
            return (this.x == other.x) && (this.y == other.y);
        }

        // Return the XOR of the x and y fields.
        public override int GetHashCode()
        {
            return x ^ y;
        }

        // Return the point's value as a string.
        public override String ToString()
        {
            return String.Format("({0}, {1})", x, y);
        }

        // Return a copy of this point object by making a simple field copy.
        public Point Copy()
        {
            return (Point)this.MemberwiseClone();
        }
    }

DateTime

获取当前系统时间
DateTime dt = DateTime.Now;
Console.WriteLine(now.ToString("yyyy-MM-dd"));
Console.WriteLine(dt.ToString()); //26/11/2009 AM 11:21:30

Console.WriteLine(dt.AddYears(1).ToString());    //         26/11/2010 PM 12:29:51
Console.WriteLine(dt.AddDays(1.1).ToString());    //        27/11/2009 PM 2:53:51
Console.WriteLine(dt.AddHours(1.1).ToString());    //       26/11/2009 PM 1:35:51
Console.WriteLine(dt.AddMilliseconds(1.1).ToString());    //26/11/2009 PM 12:29:51
Console.WriteLine(dt.AddMonths(1).ToString());    //        26/12/2009 PM 12:29:51
Console.WriteLine(dt.AddSeconds(1.1).ToString());    //     26/11/2009 PM 12:29:52
Console.WriteLine(dt.AddMinutes(1.1).ToString());    //     26/11/2009 PM 12:30:57
Console.WriteLine(dt.AddTicks(1000).ToString());    //      26/11/2009 PM 12:29:51

运算符重载

通过关键字operator后跟运算符的符号来定义的(个人认为最常见的运算符重载是+)

public static Box operator+ (Box b,Box c){
   Box box = new Box(); //创建一个对象用作运算之后的返回对象
   box.length = b.length + c.length; //对对象的内容进行处理
   box.breadth = b.breadth + c.breadth;
   box.height = b.height + c.height;
   return box; //返回对象
}

//使用
Box box3 = new Box();
box3 = box2+box1;

委托

使用delegate关键字声明委托

委托类似于c/c++中的函数指针

它可以保存某个方法的引用

委托特别用于实现事件的回调方法

所有的委托都派生自System.Delegate

//声明委托
delegate int NumberChanger(int n);
//声明委托的方法
static int AddNum(int p);

//创建委托
NumberChanger nc;
NumberChanger nc1 = new NumberChanger(AddNum)
//委托之间可以相加
nc += nc1;
//检测委托有多少个?

接口

interface MyInterface{
  void MethodToImplement();
}
//实现接口
class InterfaceImplement : MyInterface {

  public void MethodToImplement(){
    Console.WriteLine("MethodToImplement() called.");
  }
}

MyInterface iImp = new InterfaceImplement();
//调用接口
iImp.MethodToImplement();

反射

可以调用类型对象的方法访问其字段或者属性

using System;
using System.Reflection; //

[AttributeUsage (AttributeTargets.Class | //规定了特性被放在Class前面
AttributeTargets.Constructor | //规定了特性被放在构造函数前面
AttributeTargets.Field | //规定了特性被放在域的前面
AttributeTargets.Method | //规定了特性被放在方法前面
AttributeTargets.Property, AllowMuleiple = true)] //标记了我们的定制特性能否被重复放置在同一个实体多次

public class DebugInfo : System.Attribute {
  private int bugNo;
  private string developer;
  private string lastReview;
  public string message;

  public DeBugInfo(int bg, string dev, string d){
    this.bugNo = bg;
    this.developer = dev;
    this.lastReview = d;
  }

  public int BugNo{
    get {
      return bugNo;
    }
  }

  public string Developer {
    get { return developer;}

  }

  public string LastReview{
    get { return lastReview;}
  }

  public string Message {
    get { return message;}

    set { message = vallue; }
  }

  [DebugInfo(45, "Zara Ali", "12/8/2012", Message = "Return type mismatch")]
  [DebugInfo(49, "Nuha Ali", "10/10/2012", Message = "Unused variable")]
  class Rectangle {
    protected double length;
    protected double width;
    public Rectangle(double l, double w){
      length = 1;
      width = w;
    }

    [DeBugInfo(55, "Zara Ali", "19/10/2012", Message = "Return type mismatch")]
    public double GetArea(){
      return length * width;
    }

    [DeBugInfo(56, "Zara Ali", "19/10/2012")]
    public void Display(){
       Console.WriteLine("Length: {0}", length);
       Console.WriteLine("Width: {0}", width);
       Console.WriteLine("Area: {0}", GetArea());
    }
  }

  class ExecuteRectangle {
    static void Main(string[] args){
      Rectangle r = new Rectangle(4.5, 7.5);
      r.Display();
      Type type = typeof(Rectangle);
      // 遍历 Rectangle 类的特性
      foreach( Object attributes in type.GetCustomAttributes(false)){
        DeBugInfo dbi = (DeBugInfo)attributes;
        if(null != dbi){
          Console.WriteLine("Bug no: {0}", dbi.BugNo);
          Console.WriteLine("Developer: {0}", dbi.Developer);
          Console.WriteLine("Last Reviewed: {0}", dbi.LastReview);
          Console.WriteLine("Remarks: {0}", dbi.Message);
        }
      }

      //遍历方法特性
    foreach(MethodInfo m in type.GetMethods()){
      foreach(Attribute a in m.GetCustomAttributes(true)){
        DebugInfo dbi = (DebugInfo)a;
        if(null != dbi){
          Console.WriteLine("Bug no:")
          }
        }
      }
    }

  }
}

特性 调试备注

特性(Attribute) 是用于在运行时传递程序中各种元素行为信息的声明式标签,通过放置在所运营的元素前面用[]来描述

//标记已过时
[Obsolete("Dot't use OldMethod, user NewNothod")]

//自定义特性
public class DebugInfo : System.Attribute {
  private int bugNo;
  private string developer;
  private string lastReview;
  public string message;
  public DeBugInfo(int bg, string dev, string d){
    this.bugNo = bg;
    this.developer = dev;
    this.lastReview = d;
  }

  ....

}

多线程 同步

重写窗体事件DefWndProc接收自定义消息
发送消息
  string myText = textBox1.Text;
            SENDDATASTRUCT myData = new SENDDATASTRUCT();
            myData.lpData = myText;
            SendMessage(SendToHandle, MYMESSAGE, 100, ref myData);//发送自定义消息给句柄为SendToHandle 的窗口

参考资料:https://blog.csdn.net/weixin_34342992/article/details/94756731

控件部分

基础控件

Form 基础框架

工具栏

ToolStrip

ToolStripControlHost host = new ToolStripControlHost(panel);
toolStrip1.Items.Add(host);

NotifyIcon 任务栏显示气泡提示

//任务栏设置并显示气泡提示信息
        private void btn_SetInfo_Click(object sender, EventArgs e)
        {
            notifyIcon1.ShowBalloonTip(2000, "图标介绍", "柳岩身材一级棒!", ToolTipIcon.Info);
        }

        //鼠标移过图标时显示默认气泡提示信息
        private void notifyIcon1_MouseMove(object sender, MouseEventArgs e)
        {
            notifyIcon1.ShowBalloonTip(1000);
        }

https://www.cnblogs.com/ljhandsomeblog/p/11211484.html

FlowLayoutPanel()

var panel = new FlowLayoutPanel();
panel.FlowDirection = FlowDirection.BottomUp;
panel.Controls.Add(new Button(){ Text = ""})
panel.Controls.Add(new Button(){ Text = ""})

状态栏

菜单

MenuStrip menuStrip1 = new System.Windows.Forms.MenuStrip();
menuStrip1.SuspendLayout();
//一级菜单创建
this.菜单ToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();

menuStrip1.ImageScalingSize = new System.Drawing.Size(20,20);
//将一级菜单添加到menuStrip
menuStrip1.Items.AddRange(new System.Windows.Forms.ToolStripItem[]{
  this.菜单ToolStripMenuITem,
  this.帮助ToolStripMenuItem
})
menuStrip1.Location = new System.Drawing.Point(0,0);
menuStrip1.Name = "menuStrip1";
menuStrip1.Size = System.Drawing.Size(585, 28);
menuStrip1.TabIndex = 4;
menuStrip1.Text = "menuStrip1";

ToolStripMenuItem item_open;
ToolStripMenuItem item_save;
//二级菜单创建
item_open = new ToolStripMenuItem();
item_open.Name = "菜单ToolStripMenuItem"
item_open.Size = new System.Drawing.Size(53, 14);
item_open.Text = "菜单"
//将二级菜单添加到一级
菜单ToolStripMenuITem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[]{
  item_open,
  item_save
})

Button 按钮

Button btn_setting = new Button();
btn_setting.Name = "btn_setting";
btn_setting.Text = "设置";
btn_setting.Location = new System.Drawing.Point(39, 200);
btn_setting.Size = new System.Drawing.Size(495, 50);
btn_setting.TabIndex = 1;
btn_setting.UseVisualStyleBackColor = true;
btn_setting.Click += new System.EventHandler(this.Click_setting);

Label 文字标签

Label label = new Label();
label.AutoSize = true;
label.Locationo = new System.Drawing.Point(39, 139);
label.Size = new System.Drawing.Size(54,20);
label.TabIndex = 0;
label.Text = "密码";
this.Controls.Add(this.label);

TextBox 输入框

TextBox textBox = new TextBox();
textBox.Name = "textBox_pass";
textBox.PasswordChar = '*';
textBox.Size = new System.Drawing.Size(495, 27);
textBox.TabIndex = 1;

NumericUpDown 数字输入框

MumericUpDown numericUpDown1 = new NumericUpDown();
numericUpDown1.Location = new System.Drawing.Point(39,32);
numericUpDown1.Maximum = new decimal(new int[]{1000,0,0,0});
numericUpDown1.Name = "numericUpDown1";
numericUpDown1.Size = new System.Drawing.Size(150, 27);
numericUpDown1.TabIndex = 5;
numericUpDown1.Value = new decimal(new int[]{100, 0, 0, 0});

this.Controls.Add(this.numericUpDown1);

ListBox

ListBox listBox = new ListBox();
listBox.Items.Add("第一行");
//检查是否添加过
if(listBox.Items.Contains("第一行")){
  MessageBox.Show("集合成员已添加过!");
}
if(listBox.SelectedItems.Count > 0) {
  listBox.SelectedItem.ToString(); //获取选中项的值
}

ListView

//设置ListView标题栏
            this.listView.Columns.Add("车型", 120, HorizontalAlignment.Left); //
            this.listView.Columns.Add("号牌种类", 120, HorizontalAlignment.Left); //
            this.listView.Columns.Add("车牌号", 120, HorizontalAlignment.Left); //
            this.listView.Columns.Add("燃料种类", 120, HorizontalAlignment.Left); //
//设置显示模式
listView.View = View.Details;

//设置ImageList
ImageList imgList = new ImageList();
                    imgList.ImageSize = new Size(1, 20);// 设置行高 20 //分别是宽和高  

                    listView.SmallImageList = imgList; //这里设置listView的SmallImageList ,用imgList将其撑大  

//添加一个选项
                        var item = model.data[i];
                        ListViewItem lvi = new ListViewItem();

                        lvi.ImageIndex = i;     //通过与imageList绑定,显示imageList中第i项图标  

                        lvi.Text = item.CLLX;

                        lvi.SubItems.Add(item.HPZL);

                        lvi.SubItems.Add(item.HPHM);
                        lvi.SubItems.Add(item.RLZL);

                        listView.Items.Add(lvi);

https://www.cnblogs.com/ljhandsomeblog/p/11169024.html

ComboBox 下拉选择框

ComboBox comboBox = new ComboBox();
comboBox.Text = "请选择项目";
comboBox.SelectedIndex = 0;
comboBox.SelectedItem.ToString();
comboBox.Items.Add("第一项");
comboBox.Items.Add("第二项");

PictureBox

#region 控件文件拖拽获取事件
        private void img_data_DragDrop(object sender, DragEventArgs e)
        {
            //获取所有拖拽文件路劲
            System.Array array = (System.Array)e.Data.GetData(DataFormats.FileDrop);
            int index = array.Length;
            for (int i = 0; i < index; i++)
            {
                listPath.Add(array.GetValue(i).ToString());
            }

            if (listPath.Count > 0)
            {
                BindImgData(listPath[0], 1);
            }
        }

        private void img_data_DragEnter(object sender, DragEventArgs e)
        {
            if (e.Data.GetDataPresent(DataFormats.FileDrop))
            {
                e.Effect = DragDropEffects.Link;
            }
            else
            {
                e.Effect = DragDropEffects.None;
            }
        }

        /// <summary>
        /// 图片绑定
        /// </summary>
        /// <param name="path"></param>
        /// <param name="page"></param>
        private void BindImgData(string path, int page)
        {
            try
            {

                sbtn_Prev.Enabled = true;
                sbtn_Next.Enabled = true;

                if (page == 1) { sbtn_Prev.Enabled = false; }
                if (page == listPath.Count) { sbtn_Next.Enabled = false; }

                fileExtension = Path.GetExtension(path).ToLower();
                fileName = Path.GetFileName(path);
                sbtn_Pages.Text = page + "/" + listPath.Count;

                if (path.Contains("http://") || path.Contains("https://"))
                {
                    picObj = Bitmap.FromStream(new System.IO.MemoryStream((new System.Net.WebClient()).DownloadData(path)));
                }
                else
                {
                    picObj = Image.FromFile(path);
                }
            }
            catch (Exception ex)
            {
                picObj = null;
                sbtn_Pages.Text = "0";

                //string strNo = Helpers.UtilityHelper.GetSerialNumber();
                //Helpers.LogHelper.ErrorMsgRecord(this.Name, ex, strNo);
                //Helpers.LoadingHelper.CloseForm();
                //MessageBox.Show("图片对象或路径异常,显示失败!\r\n" + ex.Message + strNo, "系统提示", MessageBoxButtons.OK, MessageBoxIcon.Error);
            }

            img_data.Image = picObj;

        }

        #endregion       

        #region 鼠标移动图片
        bool dragFlag = false;
        int mouseX = 0, mouseY = 0;
        private void img_data_MouseDown(object sender, MouseEventArgs e)
        {
            mouseX = e.X;
            mouseY = e.Y;
            dragFlag = true;
        }

        private void img_data_MouseUp(object sender, MouseEventArgs e)
        {
            dragFlag = false;
        }

        private void img_data_MouseMove(object sender, MouseEventArgs e)
        {
            if (dragFlag)
            {
                img_data.Location = new Point(img_data.Location.X - (mouseX - e.X), img_data.Location.Y - (mouseY - e.Y));
            }
        }
        #endregion

https://www.cnblogs.com/ljhandsomeblog/p/11213094.html

CheckedListBox

//添加列表项,勾选指定条件的项
        private void btn_AddItem_Click(object sender, EventArgs e)
        {
            string value = txt_ItemText.Text;
            if (!string.IsNullOrWhiteSpace(value))
            {
                if (!this.checkedListBox1.Items.Contains(value))
                {
                    bool isRn = value.Contains("帅") ? true : false;
                    this.checkedListBox1.Items.Add(value, isRn);

                    checkedListBox1_SelectedIndexChanged(null, null);
                }

            }
        }
        //获取勾选项并展示
        private void checkedListBox1_SelectedIndexChanged(object sender, EventArgs e)
        {
            StringBuilder sb = new StringBuilder();
            for (int i = 0, counti = checkedListBox1.Items.Count; i < counti; i++)
            {
                if (checkedListBox1.GetItemChecked(i))
                {
                    sb.AppendFormat("{0},", checkedListBox1.GetItemText(checkedListBox1.Items[i]));
                }
            }
            this.txt_Result.Text = sb.ToString().Trim(',');
        }

https://www.cnblogs.com/ljhandsomeblog/p/11127236.html

Timer

  Enabled - 控件是否启用

  Interval - 事件的频率,多长时间触发一次时间(李献策lx
  

ProgressBar

ProgressBar progressBar = new ProgressBar();
progressBar.Name = "ProgressBar";
progressBar.Value = 40;
progressBar.Minimum = 0;
progressBar.Maximum = 100;

DataGridView

相关资料:http://m.biancheng.net/view/3040.html

操作DataTable:https://blog.csdn.net/panliuwen/article/details/47710421

TabControl

TabControl tabControl = new TabControl;
page1 = new TabPage();
page2 = new TabPage();
tabControl.Location

page1.SuspendLayout();
page2.SuspendLayout();

tabControl.SuspendLayout();

DataGridView

http://c.biancheng.net/view/3040.html

TreeView

private void btn_LoadData_Click(object sender, EventArgs e)
        {
            //设置树形组件的基础属性
            treeView1.CheckBoxes = true;
            treeView1.FullRowSelect = true;
            treeView1.Indent = 20;
            treeView1.ItemHeight = 20;
            treeView1.LabelEdit = false;
            treeView1.Scrollable = true;
            treeView1.ShowPlusMinus = true;
            treeView1.ShowRootLines = true;

            //需要加载树形的源数据
            string[] strData = { "1;内地;柳岩",
                                 "2;内地;杨幂",
                                 "3;欧美;卡戴珊",
                                 "4;日韩;李成敏",
                                 "5;日韩;宇都宫紫苑"};

            //解析到DataTable数据集
            DataTable dtData = new DataTable();
            dtData.Columns.Add("ID");
            dtData.Columns.Add("GROUP");
            dtData.Columns.Add("NAME");

            foreach (string item in strData)
            {
                string[] values = item.Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                if (values.Length == 3)
                {
                    DataRow row = dtData.NewRow();
                    row["ID"] = values[0];
                    row["GROUP"] = values[1];
                    row["NAME"] = values[2];
                    dtData.Rows.Add(row);
                }
            }

            TreeNode tn = new TreeNode();
            tn.Name = "全部";
            tn.Text = "全部";

            //将数据集加载到树形控件当中
            foreach (DataRow row in dtData.Rows)
            {
                string strValue = row["GROUP"].ToString();
                if (tn.Nodes.Count > 0)
                {
                    if (!tn.Nodes.ContainsKey(strValue))
                    {
                        BindTreeData(tn, dtData, strValue);
                    }
                }
                else
                {
                    BindTreeData(tn, dtData, strValue);
                }
            }

            treeView1.Nodes.Add(tn);
            treeView1.ExpandAll();
        }

        private void BindTreeData(TreeNode tn, DataTable dtData, string strValue)
        {
            TreeNode tn1 = new TreeNode();
            tn1.Name = strValue;
            tn1.Text = strValue;
            tn.Nodes.Add(tn1);

            DataRow[] rows = dtData.Select(string.Format("GROUP='{0}'", strValue));
            if (rows.Length > 0)
            {
                foreach (DataRow dr in rows)
                {
                    TreeNode tn2 = new TreeNode();
                    tn2.Name = dr["GROUP"].ToString();
                    tn2.Text = dr["NAME"].ToString();
                    tn1.Nodes.Add(tn2);
                }
            }
        }

        private void treeView1_AfterCheck(object sender, TreeViewEventArgs e)
        {
            //鼠标勾选树节点时需要使树节点为选中状态,反之忽略
            if (isMouseClick)
            {
                treeView1.SelectedNode = e.Node;
            }

            //获取勾选项名称
            StringBuilder sb = new StringBuilder();
            GetTreeNodesCheckName(sb, treeView1.Nodes);
            txt_CheckValue.Text = sb.ToString().Trim(';');
        }

        private void GetTreeNodesCheckName(StringBuilder sb, TreeNodeCollection tnc)
        {
            foreach (TreeNode item in tnc)
            {
                if (item.Checked) { sb.AppendFormat("{0};", item.Text); }

                GetTreeNodesCheckName(sb, item.Nodes);
            }
        }

        bool isMouseClick = true;
        private void treeView1_NodeMouseClick(object sender, TreeNodeMouseClickEventArgs e)
        {
            //选中或勾选树节点时触发子树节点或父树节点的逻辑操作
            isMouseClick = false;

            SetCheckedChildNodes(e.Node, e.Node.Checked);

            SetCheckedParentNodes(e.Node, e.Node.Checked);

            isMouseClick = true;
        }

        //树节点的父树节点逻辑操作
        private static void SetCheckedParentNodes(TreeNode tn, bool CheckState)
        {
            if (tn.Parent != null)
            {
                //当选中树节点勾选后同级所有树节点都勾选时,父树节点为勾选状态;
                //当选中树节点中的同级树节点其中有一个树节点未勾选则父树节点为未勾选状态;
                bool b = false;
                for (int i = 0; i < tn.Parent.Nodes.Count; i++)
                {
                    bool state = tn.Parent.Nodes[i].Checked;
                    if (!state.Equals(CheckState))
                    {
                        b = !b;
                        break;
                    }
                }
                tn.Parent.Checked = b ? (Boolean)false : CheckState;

                SetCheckedParentNodes(tn.Parent, CheckState);
            }
        }

        //树节点的子树节点逻辑操作
        private static void SetCheckedChildNodes(TreeNode tn, bool CheckState)
        {
            if (tn.Nodes.Count > 0)
            {
                //当前树节点状态变更,子树节点同步状态
                foreach (TreeNode tn1 in tn.Nodes)
                {
                    tn1.Checked = CheckState;

                    SetCheckedChildNodes(tn1, CheckState);
                }
            }
        }

https://www.cnblogs.com/ljhandsomeblog/p/11225879.html

DateTimePicker

CustomFormat:当Format属性设置为自定义类型时可自定义控件时间的显示格式;

Enabled:指示是否启用该控件,true为启用状态可编辑,false为禁用状态不可编辑;

MaxDate:设置控件可选择或输入的最大日期;

MinDate:设置控件可选择或输入的最小日期;

Name:指示代码中用来标识该对象的名称;

ShowUpDown:是否使用下拉日历修改日期,false为下拉日历模式,true为区域数字增减模式;

Text:与控件关联的文本,显示给用户看的内容说明;

ValueChanged事件:控件值更改时发生;

https://www.cnblogs.com/ljhandsomeblog/p/11128338.html

MonthCalender 日期控件,可选择范围

        //获取控件选中日期
        private void monthCalendar1_DateChanged(object sender, DateRangeEventArgs e)
        {
            txt_date.Text = string.Format("{0} 至 {1}", monthCalendar1.SelectionStart, monthCalendar1.SelectionEnd);

        }

MaskedTextBox 掩码文本控件,使用掩码来区分用户输入文本是否正确。

ComboBox 下拉文本框

//加载下拉项
        private void btn_LoadItem_Click(object sender, EventArgs e)
        {
            string[] strGirls = lbl_Girls.Text.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
            if (strGirls.Length > 0)
            {
                this.comboBox1.Items.Clear();
                this.comboBox1.Items.Add("全部");
                this.comboBox1.Items.AddRange(strGirls);
                this.comboBox1.SelectedIndex = 0;
                this.comboBox1.DropDownStyle = ComboBoxStyle.DropDownList;
            }
        }

https://www.cnblogs.com/ljhandsomeblog/p/11128015.html

Panel

RichTextBox

DetectUrls:指示是否自动将URL的格式设置为链接;

EnableAutoDragDrop:是否启用文本、图片和其他数据的拖放操作;

BorderStyle:指示编辑控件是否应带有边框或边框类型;

Lines:多行编辑中的文本行,作为字符串值的数组;

MaxLength:指定可以在编辑控件中输入的最大字符数;

Multiline:控制编辑控件的文本是否能够跨越多行;

ScrollBars:定义控件滚动条的行为;

WordWrap:指示多行编辑控件是否自动换行;

Enabled:指示是否启用该控件,true为启用状态用户可编辑,false为禁用状态用户不可编辑;

Name:指示代码中用来标识该对象的名称;

Text:获取或设置多格式文本框中的文本;

Rtf:获取或设置控件文本,包括所有RTF格式代码;

https://www.cnblogs.com/ljhandsomeblog/p/11214496.html

自定义控件 及 定义方法

CtrlLib.GlassButton

CtrlLib.Pager

权限系统

获取系统管理员权限

<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />

https://www.cnblogs.com/fj99/p/4239690.html?ivk_sa=1024320u

修改注册表

设置程序开机自动运行

/// <summary>  
        /// 在注册表中添加、删除开机自启动键值  
        /// </summary>  
        public static int SetAutoBootStatu(bool isAutoBoot)
        {
            try
            {
                //RegistryKey rk = Registry.LocalMachine;
                //RegistryKey rk2 = rk.CreateSubKey("Software\\Microsoft\\Windows\\CurrentVersion\\Run");
                //rk2.SetValue("MyExec", execPath);
                string execPath = Application.ExecutablePath;
                RegistryKey rk = Registry.LocalMachine;
                RegistryKey rk2 = rk.CreateSubKey("Software\\Microsoft\\Windows\\CurrentVersion\\Run");
                if (isAutoBoot)
                {
                    rk2.SetValue("MyExec", execPath);
                    Console.WriteLine(string.Format("[注册表操作]添加注册表键值:path = {0}, key = {1}, value = {2} 成功", rk2.Name, "TuniuAutoboot", execPath));
                }
                else
                {
                    rk2.DeleteValue("MyExec", false);
                    Console.WriteLine(string.Format("[注册表操作]删除注册表键值:path = {0}, key = {1} 成功", rk2.Name, "TuniuAutoboot"));
                }
                rk2.Close();
                rk.Close();
                return 0;
            }
            catch (Exception ex)
            {
                Console.WriteLine(string.Format("[注册表操作]向注册表写开机启动信息失败, Exception: {0}", ex.Message));
                return -1;
            }
        }

获取 文档/桌面/音乐/下载 目录

Environment.GetFolderPath(Environment.SpecialFolder.MyDocuments); //文档目录
string musicPath = Environment.GetFolderPath(Environment.SpecialFolder.MyMusic); //音乐目录
string tempPath = Environment.GetFolderPath(Environment.SpecialFolder.Templates); //temp目录
string desktopPath = Environment.GetFolderPath(Environment.SpecialFolder.Desktop); //桌面目录

获取应用程序所在路径
System.AppDomain.CurrentDomain.BaseDirectory
或者
System.AppDomain.CurrentDomain.SetupInformation.ApplicationBase

代码部分

设置窗口图标

this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));

设置窗口名字

this.Text = "标题";

应用全屏,隐藏状态栏

this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;

this.WindowState = System.Windows.Forms.FormWindowState.Maximized;

2、实现窗体内某控件的全屏显示

方法:例如要将richtextbox控件全屏显示,操作如下(this是当前窗体)

this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.None;
this.WindowState=FormWindowState.Maximized;
Rectangle ret = Screen.GetWorkingArea(this);

this.richTextBox2.ClientSize = new Size(ret.Width, ret.Height);
this.richTextBox2.Dock = DockStyle.Fill;
this.richTextBox2.BringToFront();

3、退出全屏,恢复原貌

方法:前提是先定义一个类成员变量,用于保存要全屏控件的原始尺寸(Size),然后在构造函数内将其初始化为控件原始尺寸

在退出全屏方法内,操作如下

this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.Sizable;
this.WindowState = FormWindowState.Normal;
this.richTextBox2.ClientSize = primarySize;//primarySize即是控件的原始尺寸
this.richTextBox2.Dock = DockStyle.None;

加载Gif图片

按钮设置点击时间

弹出对话框

 //消息框中需要显示哪些按钮,此处显示“确定”和“取消”

 MessageBoxButtons messButton = MessageBoxButtons.OKCancel;

 //"确定要退出吗?"是对话框的显示信息,"退出系统"是对话框的标题

 //默认情况下,如MessageBox.Show("确定要退出吗?")只显示一个“确定”按钮。
 DialogResult dr = MessageBox.Show("确定要退出吗?", "退出系统", messButton);

 if (dr == DialogResult.OK)//如果点击“确定”按钮

 {

   ……

 }

else//如果点击“取消”按钮

{

  ……

}

MessageBoxButtons指定若干常数,用以定义MessageBox上将显示哪些按钮(来自MSDN)

MessageBoxButtons成员:

  成员名称                                  说明

AbortRetryIgnore 消息框包含“中止”、“重试”和“忽略”按钮。

OK                                  消息框包含“确定”按钮。(默认) 
OKCancel                      消息框包含“确定”和“取消”按钮。(上例所示) 
RetryCancel      消息框包含“重试”和“取消”按钮。

YesNo                       消息框包含“是”和“否”按钮。 
YesNoCancel          消息框包含“是”、“否”和“取消”按钮

弹出带输入框的对话框

修改窗口固定宽高,不允许修改

窗口可自由设置宽高

设置按钮样式(背景色,文字颜色,字体,字体大小)

加载本地图片

fileStream = new FileStream("图片路径", FileMode.Open, FileAccess.Read);
pictureBox1.Image = Image.FromStream(fileStream);

加载resouce图片

pictureBox1.Image = Properties.Resources.headimg_dl_android;

加载网络图片

this.QRCodePictureBox.LoadAsync(“https://injiajia.com/qrcode.png”);

播放声音

//System.Media.SystemSounds.Asterisk.Play(); //系统提示音
            //System.Media.SystemSounds.Beep.Play(); //系统提示音
            //System.Media.SystemSounds.Exclamation.Play(); 
            System.Media.SystemSounds.Hand.Play(); //错误提示
            //System.Media.SystemSounds.Question.Play(); //没有听到声音

2.使用System.Media.SoundPlayer播放wav
System.Media.SoundPlayer sp = new SoundPlayer(); 
sp.SoundLocation = @"D:/10sec.wav"; 
sp.PlayLooping();

3.使用MCI Command String多媒体设备程序接口播放mp3,avi等
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.InteropServices;

namespace MyWenxinTool
{
    public class musicplay
    {

        public static uint SND_ASYNC = 0x0001;
        public static uint SND_FILENAME = 0x00020000;
        [DllImport("winmm.dll")]
        public static extern uint mciSendString(string lpstrCommand, string lpstrReturnString, uint uReturnLength, uint hWndCallback);

        public static void PlayNmusinc(string path)
        {
            mciSendString(@"close temp_alias", null, 0, 0);
            mciSendString(@"open """+path+@""" alias temp_alias", null, 0, 0);
            mciSendString("play temp_alias repeat", null, 0, 0);
        }

        /// <summary>
        /// 播放音乐文件(重复)
        /// </summary>
        /// <param name="p_FileName">音乐文件名称</param>
        public static void PlayMusic_Repeat(string p_FileName)
        {
            try
            {
                mciSendString(@"close temp_music", " ", 0, 0);
                mciSendString(@"open " + p_FileName + " alias temp_music", " ", 0, 0);
                mciSendString(@"play temp_music repeat", " ", 0, 0);
            }
            catch
            { }
        }

        /// <summary>
        /// 播放音乐文件
        /// </summary>
        /// <param name="p_FileName">音乐文件名称</param>
        public static void PlayMusic(string p_FileName)
        {
            try
            {
                mciSendString(@"close temp_music", " ", 0, 0);
                //mciSendString(@"open " + p_FileName + " alias temp_music", " ", 0, 0);
                mciSendString(@"open """ + p_FileName + @""" alias temp_music", null, 0, 0);
                mciSendString(@"play temp_music", " ", 0, 0);
            }
            catch
            { }
        }

        /// <summary>
        /// 停止当前音乐播放
        /// </summary>
        /// <param name="p_FileName">音乐文件名称</param>
        public static void StopMusic(string p_FileName)
        {
            try
            {
                mciSendString(@"close " + p_FileName, " ", 0, 0);
            }
            catch { }
        }

    }

}

保存ini数据

 public class ReadIni
    {
        // 声明INI文件的写操作函数 WritePrivateProfileString()

        [System.Runtime.InteropServices.DllImport("kernel32")]

        private static extern long WritePrivateProfileString(string section, string key, string val, string filePath);

        // 声明INI文件的读操作函数 GetPrivateProfileString()

        [System.Runtime.InteropServices.DllImport("kernel32")]

        private static extern int GetPrivateProfileString(string section, string key, string def, System.Text.StringBuilder retVal, int size, string filePath);

        private string sPath = null;
        public ReadIni(string path)
        {
            this.sPath = path;
        }

        public void Writue(string section, string key, string value)
        {

            // section=配置节,key=键名,value=键值,path=路径

            WritePrivateProfileString(section, key, value, sPath);

        }
        public string ReadValue(string section, string key)
        {

            // 每次从ini中读取多少字节

            System.Text.StringBuilder temp = new System.Text.StringBuilder(255);

            // section=配置节,key=键名,temp=上面,path=路径

            GetPrivateProfileString(section, key, "", temp, 255, sPath);

            return temp.ToString();

        }

    }

生成json数据

JsonObject json = new JsonObject();
 json["key"] = objDE.Value;
 Console.WriteLine(json.ToString());

保存xml数据

json格式化

配置应用名称、版本号、

获取应用名称、版本号

Windows应用签名

WIndows应用加固

Windows应用压缩

打开文件对话框

打开文件夹对话框

动画

平移动画

缩放动画

透明度渐变动画

高级

使用sqlite数据库

https://www.cnblogs.com/springsnow/p/13072915.html

使用sql server数据库

https://www.cnblogs.com/wangxueliang/p/9346470.html

使用mysql数据库

使用oracle数据库

实现socket server websocket

“Fleck”包 websocket-sharp包 WebSocket4Net

https://blog.csdn.net/qq_35955916/article/details/86529647

文件读写

https://www.cnblogs.com/kafeibuku/p/5320350.html

加载http数据

下载文件

实现http服务器

串口通信

 public class Comm   
     {
        public delegate void EventHandle(byte[] readBuffer);
        public event EventHandle DataReceived;

        public SerialPort serialPort;
        Thread thread;
        volatile bool _keepReading;

        public Comm()
        {
            serialPort = new SerialPort();
            thread = null;
            _keepReading = false;
        }

        public bool IsOpen
        {
            get 
            {
                return serialPort.IsOpen;
            }
        }        

        private void StartReading()
        {
            if (!_keepReading)
            {
                _keepReading = true;
                thread = new Thread(new ThreadStart(ReadPort));
                thread.Start();
            }
        }

        private void StopReading()
        {
            if (_keepReading)
            {
                _keepReading = false;
                thread.Join();
                thread = null;                
            }
        }

        private void ReadPort()
        {
            while (_keepReading)
            {
                if (serialPort.IsOpen)
                {
                    int count = serialPort.BytesToRead;
                    if (count > 0)
                    {
                        byte[] readBuffer = new byte[count];
                        try
                        {
                            Application.DoEvents();
                            serialPort.Read(readBuffer, 0, count);
                            if(DataReceived != null)
                                DataReceived(readBuffer);
                            Thread.Sleep(100);
                        }
                        catch (TimeoutException)
                        {
                        }
                    }
                }
            }
        }

        public void Open()
        {
            Close();            
            serialPort.Open();
            if (serialPort.IsOpen)
            {
                StartReading();
            }
            else
            {
                MessageBox.Show("串口打开失败!");
            }
        }

        public void Close()
        {
            StopReading();
            serialPort.Close();
        }

        public void WritePort(byte[] send, int offSet, int count)
        {
            if (IsOpen)
            {
                serialPort.Write(send, offSet, count);
            }
        }
    }

注册串口

 Comm    comm = new Comm();
            ConfigClass config = new ConfigClass();
            comm.serialPort.PortName = config.ReadConfig("SendHealCard");
            //波特率
            comm.serialPort.BaudRate = 9600;
            //数据位
            comm.serialPort.DataBits = 8;
            //两个停止位
            comm.serialPort.StopBits = System.IO.Ports.StopBits.One;
            //无奇偶校验位
            comm.serialPort.Parity = System.IO.Ports.Parity.None;
            comm.serialPort.ReadTimeout = 100;
    comm.serialPort.WriteTimeout = -1; 

      comm.Open();
            if (comm.IsOpen)
            {
                comm.DataReceived += new Comm.EventHandle(comm_DataReceived);
            }
//https://www.cnblogs.com/binfire/archive/2011/10/08/2201973.html

http://www.360doc.com/content/13/0829/09/7531335_310657574.shtml

解析json

方法一:
  model = JsonConvert.DeserializeObject<JSONModel>(reString);
方法二:(.NET Framework4.0不支持)
  JsonObject jsonObject = new JsonObject(reString,true);

解析xml

方法一:
JsonObject jsonobj = new JsonObject();
jsonobj.LoadXml("<string name=\"haha\" value=\"\"/>");
Console.WriteLine(jsonobj.ToString());
方法二:
   XmlDocument xmlDoc = new XmlDocument();  
    xmlDoc.LoadXml("<?xml version=\"1.0\" encoding=\"utf-8\"?><HH><CODE>11</CODE><NAME>kkkk</NAME></HH>");  
    XmlNode rootNode = xmlDoc.SelectSingleNode("HH");  
    foreach (XmlNode xxNode in rootNode.ChildNodes)  
    {  
        string dsf = xxNode.InnerText;  
        string sdf = xxNode.Name;  
    } 

https://www.cnblogs.com/hnsongbiao/p/5636076.html

反射解析json

生成excel

https://www.cnblogs.com/sdflysha/archive/2019/08/26/20190824-dotnet-excel-compare.html

生成doc

https://blog.csdn.net/a13407142317/article/details/104210356s

生成pdf

内嵌视频播放器vlc

 VlcPlayerBase player;
   string pluginPath = Environment.CurrentDirectory + "\\plugins\\";  //插件目录
            player = new VlcPlayerBase(pluginPath);
            player.SetRenderWindow((int)panel1.Handle);//panel

内嵌网页浏览器

WebBrowser

识别二维码

using ThoughtWorks.QRCode.Codec;
using ThoughtWorks.QRCode.Codec.Data;
/// <summary>
        /// 读取图片文件,识别二维码
        /// </summary>
        /// <param name="filePath">图片文件路劲</param>
        /// <returns>识别结果字符串</returns>
        public static string CodeDecoder(string filePath)
        {
            string decoderStr;
            try
            {
                if (!System.IO.File.Exists(filePath))//判断有没有需要读取的主文件夹,如果不存在,终止
                    return null;

                Bitmap bitMap = new Bitmap(Image.FromFile(filePath));//实例化位图对象,把文件实例化为带有颜色信息的位图对象

                QRCodeDecoder decoder = new QRCodeDecoder();//实例化QRCodeDecoder

                //通过.decoder方法把颜色信息转换成字符串信息
                decoderStr = decoder.decode(new QRCodeBitmapImage(bitMap), System.Text.Encoding.UTF8);
            }
            catch (Exception ex)
            {
                throw ex;
            }
            Console.WriteLine(decoderStr);
            return decoderStr;//返回字符串信息
        }

识别条形码

需要 libzbar.dll libzbar-cli.dll libiconv-2.dll

 /// <summary>
        /// 条码识别
        /// </summary>
        private void ScanBarCode(string fileName)
        {
            DateTime now = DateTime.Now;
            Image primaryImage = Image.FromFile(fileName);

            Bitmap pImg = MakeGrayscale3((Bitmap)primaryImage);
            using (ZBar.ImageScanner scanner = new ZBar.ImageScanner())
            {
                scanner.SetConfiguration(ZBar.SymbolType.None, ZBar.Config.Enable, 0);
                scanner.SetConfiguration(ZBar.SymbolType.CODE39, ZBar.Config.Enable, 1);
                scanner.SetConfiguration(ZBar.SymbolType.CODE128, ZBar.Config.Enable, 1);

                List<ZBar.Symbol> symbols = new List<ZBar.Symbol>();
                symbols = scanner.Scan((Image)pImg);

                if (symbols != null && symbols.Count > 0)
                {
                    string result = string.Empty;
                    symbols.ForEach(s => result += "条码内容:" + s.Data + " 条码质量:" + s.Quality + Environment.NewLine);
                    MessageBox.Show(result);
                }
            }
        }

        /// <summary>
        /// 处理图片灰度
        /// </summary>
        /// <param name="original"></param>
        /// <returns></returns>
        public static Bitmap MakeGrayscale3(Bitmap original)
        {
            //create a blank bitmap the same size as original
            Bitmap newBitmap = new Bitmap(original.Width, original.Height);

            //get a graphics object from the new image
            Graphics g = Graphics.FromImage(newBitmap);

            //create the grayscale ColorMatrix
            System.Drawing.Imaging.ColorMatrix colorMatrix = new System.Drawing.Imaging.ColorMatrix(
               new float[][] 
              {
                 new float[] {.3f, .3f, .3f, 0, 0},
                 new float[] {.59f, .59f, .59f, 0, 0},
                 new float[] {.11f, .11f, .11f, 0, 0},
                 new float[] {0, 0, 0, 1, 0},
                 new float[] {0, 0, 0, 0, 1}
              });

            //create some image attributes
            ImageAttributes attributes = new ImageAttributes();

            //set the color matrix attribute
            attributes.SetColorMatrix(colorMatrix);

            //draw the original image on the new image
            //using the grayscale color matrix
            g.DrawImage(original, new Rectangle(0, 0, original.Width, original.Height),
               0, 0, original.Width, original.Height, GraphicsUnit.Pixel, attributes);

            //dispose the Graphics object
            g.Dispose();
            return newBitmap;
        }

播放视频直播流

视频边下边播

string char bytes互相转换

//传gbk编码
byte[] buffer = Encoding.GetEncoding("GBK").GetBytes(str)
//转utf8编码
byte[] buffer = Encoding.GetEncoding("UTF-8").GetBytes(str)

//string转byte[]:
byte[] byteArray = System.Text.Encoding.Default.GetBytes ( str );

//byte[]转string:
string str = System.Text.Encoding.Default.GetString ( byteArray );

NetWorkStream类的主要属性

 NetworkStream netStream = new NetworkStream(mesock);
 byte[] nyByte = new Byte[1024];
 // Read() :
 netStream.Read(myByte, 0, myByte.Length);
 // Write():
 netStream.Write(myByte, 0, myByte.Length);
 netStream.Flush();

画圆 画线

Graphics g = this.CreateGraphics();
g.DrawLine(new Pen(Color.Black,10.0f),new Point(10,10),new Point(100,10));
g.DrawRectangle(new Pen(Color.Black, 1.0f), new Rectangle(0, 0, 30, 30));
g.DrawEllipse(new Pen(Color.Black, 1.0f), new Rectangle(0, 0, 30, 30));

使用VLC播放器

https://blog.csdn.net/exalgentle/article/details/80303955

https://www.cnblogs.com/tiandi/p/6252580.html

第三方UI库

WPF设置主题:

<!-- 只需要加下面一句 -->
        <ResourceDictionary Source="J:\vs\wpfthemes主题\WPF.Themes\BubbleCreme\Theme.xaml"/>

自定义的UI组件库:https://www.cnblogs.com/anding/p/4715440.html

https://github.com/kwwwvagaa/NetWinformControl/blob/master/README_CN.md

https://gitee.com/yhuse/SunnyUI#note_4015807

使用Material Design : https://blog.csdn.net/YouyoMei/article/details/99816982

UI库合集:https://www.zhihu.com/question/311160143/answer/1340958261

WinCE

C#调用C语言dll库

https://blog.csdn.net/YouyoMei/article/details/103535978

变量对应关系说明:https://docs.microsoft.com/zh-cn/dotnet/framework/interop/marshaling-data-with-platform-invoke

连接mysql:https://forums.mysql.com/read.php?38,67281,67917

平台调用数据类型

下表列出了 Windows API 和 C 样式函数中使用的数据类型。 许多非托管库包含将这些数据类型作为参数和返回值传递的函数。 第三列列出了相应的 .NET Framework 内置值类型或可在托管代码中使用的类。 在某些情况下,你用相同大小的类型替代表中列出的类型。

Windows API 中的非托管类型 非托管 C 语言类型 托管类型 描述
VOID void System.Void 应用于不返回值的函数。
HANDLE void * System.IntPtrSystem.UIntPtr 在 32 位 Windows 操作系统上为 32 位、在 64 位 Windows 操作系统上为 64 位。
BYTE unsigned char System.Byte 8 位
SHORT short System.Int16 16 位
WORD unsigned short System.UInt16 16 位
INT int System.Int32 32 位
UINT unsigned int System.UInt32 32 位
LONG long System.Int32 32 位
BOOL long System.BooleanSystem.Int32 32 位
DWORD unsigned long System.UInt32 32 位
ULONG unsigned long System.UInt32 32 位
CHAR char System.Char 使用 ANSI 修饰。
WCHAR wchar_t System.Char 使用 Unicode 修饰。
LPSTR char * System.StringSystem.Text.StringBuilder 使用 ANSI 修饰。
LPCSTR const char * System.StringSystem.Text.StringBuilder 使用 ANSI 修饰。
LPWSTR wchar_t * System.StringSystem.Text.StringBuilder 使用 Unicode 修饰。
LPCWSTR const wchar_t * System.StringSystem.Text.StringBuilder 使用 Unicode 修饰。
FLOAT float System.Single 32 位
DOUBLE double System.Double 64 位

有关 Visual Basic、C# 和 C++ 中的相应类型,请参阅 .NET Framework 类库简介

发表评论

邮箱地址不会被公开。 必填项已用*标注