• 1. 4、SQL1、C#编程基础2、C#面向对象3、WinForm基础 学习线路图5、ADO.NET9、JQuery6、HTML7、javaScript8、DOM10、asp.net基础11、asp.net中级12、asp.net高级13、Ajax14、项目实践
  • 2. C#编程基础从零开始
  • 3. .Net开发环境(*了解).Net FrameworkC#VB.NetF#……开发工具:Visual Studio点Net、Dot NetC SharpIronPython提供函数库、类库
  • 4. 北京传智播客教育 www.itcast.cn .Net简介(*了解).Net FrameworkCLR操作系统应用程序应用程序操作系统平台无关:CLR、.Net Framework进行了隔离。Windows、Linux(Mono)、智能手机、Web、RIA。学会.Net什么都能开发,知识移植。更安全、更省心:代码托管、罕用指针、垃圾回收。语言无关:VB.Net、C#都调用同样的类、同样的方法,VB.Net写的类C#也可以调用。模糊了语言的差别
  • 5. .Net 的版本(*了解).Net 1.1.Net 2.0 .Net3.x.Net4.x……Visual Studio2003Visual Studio2005Visual Studio2008Visual Studio2010……向下兼容大同小异Express(免费版) 快捷版Standard 标准版Professional 专业版Team Suite 团队版常用的功能没啥差别,微软的定价策略
  • 6. 第一个C#程序创建第一个控制台程序并且调试运行。 为什么要从控制台程序开始?不要把精力放到表现层,而是把精力放到写代码上。无论控制台还是Winform还是ASP.Net最难的是写代码,而不是拖控件。 唯一需要学的三条控制台指令: Console.WriteLine:打印输出、 Console.ReadLine:从控制台读入一行、Console.ReadKey:控制台暂停。 至于Console.是什么意思不用管。1+1=2的例子 占位符是个什么玩意儿?{0}的个数必须和参数的个数一样,是一一对应的关系。
  • 7. VS开发环境介绍解决方案管理器:解决方案、工程、文件 C#源文件一般以cs结尾 C#程序的入口是Main函数,在Main中写代码就行,暂时不用关心其他部分是什么意思 错误列表。见到编译错误不用慌。错误排除演示。常见错误:结尾没有分号,大小写错误。 显示代码行号。工具→选项→文本编辑器→C#→显示→行号
  • 8. C#语法从上到下一条条的依次执行。 大小写敏感 函数参数用()包围 两句代码之间用分号(;)分割(易错:全角问题) 注释:单行注释、多行注释。
  • 9. 变量把变量看成放数据的容器。 定义变量的方式:类型 变量名; int i3; 变量的类型:不同类型的容器放不同的东西,铁罐不能放硫酸。不能在int类型的变量中放字符串。 变量不能放和变量类型不兼容的数据。 问题变量的名字不能重名(不严格) int i=10;Console.WriteLine("i");
  • 10. 常用基本数据类型string、int 、char 、bool 、decimal (了解) 、byte(了解)、double(了解)、long(了解)、float(了解)等。 bool的取值:true、false。 为什么输出"要用转义符"\"",因为编译器默认是遇到"开始字符串,再遇到"是结束字符串,但是如果遇到前面有\的"就不把它当成有字符串起始意义的"。 string:"\"ab\""、"ab\nb"、"c:\\a.txt"、@"c:\a.txt"(推荐)。@表示字符串中的\不当成转义符 @不是万能的,不能解决字符串中有双引号的问题,如果有双引号还是用转义符 ‘a’是char,"a"是string string s = Console.ReadLine(); 问题: String str=Console.ReadLine(); Console.WriteLine(str); 用户输入a\nb,输出什么?转义符只针对在代码中直接写出的字符串,对于程序中读取出来没有这个问题。 简单的类型转换:Convert.ToString()、ToString()、Convert.ToInt32() 。 输入一个数,打印这个数的平方。
  • 11. 补充问题:int i=Convert.ToInt32(Console.ReadLine()) string s1 = Console.ReadLine(); int i = Convert.ToInt32(s1); @可以表示多行字符串。
  • 12. 变量的命名命名规则:第一个字符必须是字母或者下划线(_),其后的字符可以是任意个数字、字母、下划线。不能全部使用C#的关键字,比如class、namespace、new、void等。判断方式:VS中亮蓝色的就是关键字。 这也是类、函数等的命名规则。 中文变量名(类名、函数名)。 C#中建议变量的开头用小写。 下列哪个是正确的变量名?_a、a、a1、a_a、1_a、a1、1a、a3_、a$b、int、int1、a b、A1、INT。 变量的声明:int i;int x,y;int i=3;
  • 13. 运算符、表达式+、-、*(乘)、/(除)、%(求余) +可以用作字符串连接,其他不可以。 ++(自增)、--(自减) (*)运算符优先级:i1+i2*i3、(i1+i2)*i3。不要变态,括号是王道。 变量可以和字面量混合运算。 练习:让用户输入两个数,打印出两个数的和。 练习:让用户输入一个半径,打印出圆的面积。
  • 14. 赋值赋值运算符=,让左边变量的值等于右边的计算结果。这就能解释令人不解的i=i+1; (*)+=、-=、*=、/=。 i2=i1++;i2=++i1;(了解)。--同理。 习题:int a=10;a++;a=a+a;Console.WriteLine("{0}",a);执行结果是什么? int i=10;int j=i;i=5;j=? int x=10;x+y=80;Console.WriteLine(y); x + y = 80; //左边的必须是变量!!!不能是常量,不能是表达式 习题:交换两个变量的值
  • 15. 布尔运算相等判断:==,不要和=混淆。WriteLine("{0}",i==1);WriteLine("{0}",i=1);的区别。Console.WriteLine("{0}",i=1);//C#中赋值表达式也有值,它的值表示为赋值后变量的值true;false; 不等判断:!= 大小比较:<、>、<=、>= 取反:! 组合运算:&&(并且)、||(或者)。 && 并且:只有两边都为true的时候,表达式的值才为true,否则是false; ||或者:两边只要有一个为true的时候,表达式的值就是true,否则是false;
  • 16. ifif(i>1) { }if(i>1) { } else { }if(i>100) { } else if(i<10) { } else { }单句的时候大括号可以省略,但是不建议省略,演示说明whyif语句的嵌套if(i>100||i<10) { }if(i>100&&j>10) { }if((i>0&&j>0)||(i<0&&j<0)) { }易错代码: if(i>10); { Console.WriteLine("是"); }
  • 17. 课上练习学编程不是看书,不是听老师讲,而是自己动手写。 作业1:提示用户输入密码,如果密码是“888888”则提示正确,否则提示错误。 作业2:提示用户输入密码,如果密码是“888888”则提示正确,否则要求再输入一次,如果密码是“888888”则提示正确,否则提示错误。 作业3:提示用户输入用户名,然后再提示输入密码,如果用户名是“admin”并且密码是“888888”,则提示正确,否则提示错误,如果用户名不是admin还提示用户用户名不存在。 作业4:提示用户输入年龄,如果大于等于18,则告知用户可以查看,如果小于10岁,则告知不允许查看,如果大于等于10岁,则提示用户是否继续查看(yes、no),如果输入的是yes则提示用户可以查看,否则提示不可以查看。(测试边界条件,-1,8888888888888888888888888,aaaa。微软如狼似虎的Tester) 作业5:依次提示用户输入两个整数(假设i1、i2)。如果i1、i2都是正数,则将i1的值递增一个数,然后打印i1+i2的值;如果i1、i2都是负数,则将i1的值递减10个数,然后打印i1*i2的值;如果i1、i2中任一个为0,则提示数据有错误;否则计算i1*i2的绝对值。 注意:变量命名要用有意义的变量名。
  • 18. switch case类似于if...else...else if...else,但是是离散值的判断。 switch一般都可以用if重写,但是if不一定能用switch重写 不要忘了break。C#中的break不写是不行的,除了合并case的情况switch(i) case 1: // break; case 2: // break;switch(i) case 1: // break; case 2: // break; default: break;case中的值必须是常量,不能是变量、表达式。 switch(i) case a: // break;switch(i) case 1: case 2: // break;被判定的值进入满足条件的分支执行
  • 19. while循环while(i<100) { //打印i i++; } 只要while后小括号中的表达式为true,就不断执行大括号中的代码 while(不是终点) { 跑 }do { //打印i i++; } while(i<100) 先做……如果满足则再来一次,直至while表达式为false。至少被执行一次。(*)练习1:用while计算1到100之间整数的和;(有更好的数学解法) 练习2:要求用户输入用户名和密码,只要不是admin、888888就一直提示要求重新输入。 练习3:不断要求用户输入一个数字,然后打印这个数字的二倍,当用户输入q的时候程序退出(return)。 练习4:不断要求用户输入一个数字(假定用户输入的都是正整数),当用户输入end的时候显示刚才输入的数字中的最大值。设一个变量int max,初始值为0,用户每输入一次就把用户输入的和max比较一下,如果输入的比max大,则让max等于用户输入。
  • 20. 循环的中断break:立即终止整个循环。 continue:立即终止当前循环步骤,进行下一次循环步骤。 练习1:用 while continue实现计算1到100之间的除了能被7整除之外所有整数的和。 练习2:用while break实现要求用户输入用户名和密码,只要不是admin、888888就一直提示要求重新输入。 练习3:编写聊天机器人,如果问“今天天气怎么样?”则回答天气,如果问……,如果说“88”,则“再见”。
  • 21. for循环for(code1;code2;code3)。code1:循环的初始化代码,只在循环开始之前运行一次;code2,bool类型的表达式,每次循环完成前都判断一下是否为true,只有为true才会进行本次循环;code3在每次循环之后执行一次。 for的三段都可以省略,但是不能丢了“;”。 break、continue同样可以应用于for。 for和while代码之间都可以互相转换,究竟用哪种方式则取决于一些惯用用法和个人习惯,不用记,代码写多了自然就有感觉for(int i=0;i<10;i++) { }for(int i=100;i>0;i--) { }for中终止条件注意是<还是<= 用 for实现计算1到100之间所有整数的和。用 for实现计算200到300之间所有整数的和。 常见编程问题:插入、覆盖模式的困惑。
  • 22. 类型转换Cast(*)把源类型赋值给目标类型,两个类型不一致的时候会发生类型转换。a=b,b是源,a是目标 隐式转换、显式转换。当目标类型一定能满足源类型转换过去后的要求的话就是隐式转换;如果当目标类型不一定能满足源类型转换过去后的要求的话就需要显式转换(程序员自己负责)。 把中国人转换为人是隐式转换,把人转换为中国人则是显式转换(强制转换) 内存中的数据没有变化,只是不同的视角而已。 byte b=1;int i=1;i = b;b = (byte)i; 为什么要显式转换?编译器不能保证一定正确,转换结果自己负责。要人给一个中国人当前没问题,但是要中国人给一个人则可能有问题,编译器不承担这个责任,由开发人员来保证。 只有在内存存储上存在交集的类型之间才能进行Cast,否则则不可以,比如不可以int i;string s=(string)i;反之也不可以。这种情况必须用Convert类提供的方法。
  • 23. 类型转换ConvertConvert不再是内存级别的转换,而是考虑数据意义的转换。可以把姓名Convert成人。Convert是一个加工、改造的过程 Convert.ToInt32、Convert.ToString、每种类型都还有ToString方法(类型的ToString和Convert.ToString略微的差别暂时不用关心)
  • 24. 枚举确定数量、确定值的几个取值:东西南北、男女、上中下。enum Gender{male,female} enum QQStatus{online,offline,hidden}枚举的用法,QQStatus status = QQStatus.online; 和用字符串比起来,用枚举的好处就是限定了变量的取值范围,程序处理起来更方便。
  • 25. 数组保存多个值。几乎任意类型都可以声明数组。int[] nums = {5,3,8}int[] nums = new int[3]int[] nums = new int[3]{5,3,8}//个数和声明数必须一致 int[] nums = new int[5]{5,3,8}//错误 使用索引器访问指定编号位置的元素,访问数组元素:nums[0]、nums[1]。索引从0开始。取到的元素的类型就是数组元素的类型。还可以对数组元素进行赋值练习1:从一个整数数组中取出最大的整数 练习2:计算一个整数数组的所有元素的和。 练习3:将一个字符串数组输出为|分割的形式,比如“梅西|卡卡|郑大世” 练习4:将一个整数数组的每一个元素进行如下的处理:如果元素是正数则将这个位置的元素的值加1,如果元素是负数则将这个位置的元素的值减1。 练习5:有一个整数数组,请声明一个字符串数组,将整数数组中的每一个元素的值转换为字符串保存到字符串数组中。string[] strs = new string[values.Length]; 练习6:将一个字符串数组的元素的顺序进行反转。{"3","a","8","haha"} {"haha","8","a","3"}。第i个和第length-i-1个进行交换。
  • 26. 调查是否需要延长练习时间、降低讲课的难度
  • 27. 数组2foreach循环 string[] names= {"tom","jerry","lily"}; foreach(string name in names) { Console.WriteLine("我的名字{0}",name); } 和for的区别:for可以不逐个遍历,比如每隔一个遍历一个,或者可以从后向前遍历
  • 28. 函数函数就是将一堆代码进行重用的一种机制。函数就是一段代码,这段代码可能有输入的值(参数),可能会返回值。一个函数就像一个专门做这件事的人,我们调用它来做一些事情,它可能需要我们提供一些数据给它,它执行完成后可能会有一些执行结果给我们。要求的数据就叫参数,返回的执行结果就是返回值。 Console.ReadLine就是一个有返回结果的函数;Console.WriteLine("hello")就是一个有执行参数的函数,只有告诉WriteLine被打印的数据它才知道如何打印;int i= Convert.ToInt32("22")则是一个既有参数又有返回值的函数。 有了函数写代码就像拼积木,C#中的各种各样的技术其实就是通过for、if等这些基础的语法将不同的函数按照一定的逻辑组织起来。
  • 29. 自己写函数1 读取输入的整数,定义成函数,多次调用 static int ReadInt() { String s = Console.ReadLine(); return Convert.ToInt32(s); } 写程序测试,程序调用到函数的时候是进入函数内部执行的,执行完毕再继续向下执行。 2、函数如果没有返回值则标记返回值类型为void 3、return语句 导致函数立即返回。在返回值为void的函数中return,在返回值非void的函数中return数值
  • 30. 函数返回值易错点一个函数如果“答应”返回一个非void类型的值,则函数的所有路径都要有返回值。比如将对输入年龄转换为年龄段描述的函数。
  • 31. 函数参数计算两个整数中的最大值:int Max(int i1,int i2) 计算输入数组的和:int Sum(int[] values) 确定函数参数的原则:自己能确定的数据自己内部解决,自己确定不了的数据通过参数传递。 练习:string[] strs={"aa","333","ccc"}; 返回给我一个字符串,然后字符串使用我指定的分隔符来进行分割,比如我指定用"|"分割,那么返回给我"aa|333|ccc"。 string Join(string[] strs,string seperator) 问题:函数名开头大写,参数名开头小写,参数名、变量名要有意义
  • 32. 可变参数参数数组:int sum(params int[] values) int sum(string name,params int[] values) 可变参数数组必须是最后一个 参数默认值(.Net4.0) :void SayHello(string name,int age=20)(*了解)
  • 33. 函数重载(函数重名)函数的重名:错误 static void SayHello(string name) { Console.WriteLine("我是{0}",name); } static void SayHello(string name) { Console.WriteLine("I am{0}",name); }static void SayHello(string name) { Console.WriteLine("我是{0}",name); } static void SayHello(int age) { Console.WriteLine("我的年龄{0}",age); }static void SayHello(string name) 错误 { Console.WriteLine("我是{0}",name); } static int SayHello(string name) { return 10; }static void SayHello(string name) { Console.WriteLine("我是{0}",name); } static void SayHello(string name,string nickname) { Console.WriteLine("我是{0},昵称是{1}",name,nickname); }构成重载的条件:参数类型不同或者参数个数不同(不严谨的),与返回值无关。
  • 34. 字符串的处理C#中单个字符用单引号包含就是char类型,('a'),单引号中放且只能放一个字符。 单个字符也可以表示为字符串,还可以有长度为0的字符串 使用s.Length属性来获得字符串中的字符个数 string可以看做是char的只读数组。char c = s[1];。例子:遍历输出string中的每个元素。 C#中字符串有一个重要的特性:不可变性,字符串一旦声明就不再可以改变。所以只能通过索引来读取指定位置的char,不能对指定位置的char进行修改。 如果要对char进行修改,那么就必须创建一个新的字符串,用s. ToCharArray()方法得到字符串的char数组,对数组进行修改后,调用new string(char[])这个构造函数(暂时不用细研究)来创建char数组的字符串。一旦字符串被创建,那么char数组的修改也不会造成字符串的变化。例子:将字符串中的A替换为a。
  • 35. 常见疑问谁说字符串不可变?string s = "abc";s="123",s这不是变了吗 要区分变量名和变量指向的值的区别。程序中可以有很多字符串,然后由字符串变量指向他们,变量可以指向其他的字符串,但是字符串本身没有变化。字符串不可变性指的是内存中的字符串不可变,而不是变量不变。 string s10 = s1;//s10指向s1指向的字符串,而不是s10指向s1,哪怕s1以后指向了其他内存,那么s10还是指向"hello"abcadmin888888s1s1
  • 36. String类常用函数ToLower():得到字符串的小写形式。 注意字符串是不可变的,所以这些函数都不会直接改变字符串的内容,而是把修改后的字符串的值通过函数返回值的形式返回。s.ToLower()与s=s.ToLower() ToUpper():得到字符串的大写形式; Trim()去掉字符串两端的空白。 s1.Equals(s2, StringComparison.OrdinalIgnoreCase),两个字符串进行比区分大小写的比较。
  • 37. 字符串的分割string[] Split(params char[] separator):将字符串按照指定的分割符分割为字符串数组; string[] Split(char[] separator, StringSplitOptions options)将字符串按照指定的char分割符分割为字符串数组( options 取RemoveEmptyEntries的时候移除结果中的空白字符串); string[] Split(string[] separator, StringSplitOptions options)将字符串按照指定的string分割符分割为字符串数组。 例子1:从日期字符串("2008-08-08")中分析出年、月、日;2008年08月08日。 例子2:从一个记录了学生成绩的文本文档,每个学生成绩是一行,每行是用|分割的数据,用|分割的域分别是姓名、年龄、成绩,写程序取出成绩最高学生的姓名和成绩。参考:使用string[] lines = System.IO.File.ReadAllLines(@"c:\root.ini", Encoding.Default);从文本文件读取数据,返回值为string数组,每个元素是一行。
  • 38. 字符串函数详解字符串替换:string Replace(string oldValue, string newValue)将字符串中的出现oldValue的地方替换为newValue。例子:名字替换。 取子字符串:string Substring(int startIndex),取从位置startIndex开始一直到最后的子字符串; string Substring(int startIndex, int length),取从位置startIndex开始长度为length的子字符串,如果子字符串的长度不足length则报错。 bool Contains(string value)判断字符串中是否含有子串value bool StartsWith(string value)判断字符串是否以子串value开始; bool EndsWith (string value)判断字符串是否以子串value结束; int IndexOf(string value):取子串value第一次出现的位置。
  • 39. 字符串的处理练习课上练习1:接收用户输入的字符串,将其中的字符以与输入相反的顺序输出。"abc"→"cba" 课上练习2:接收用户输入的一句英文,将其中的单词以反序输出。"hello c sharp"→"sharp c hello" 课上练习3:从Email中提取出用户名和域名:abc@163.com。IndexOf找到@的位置。SubString。 课上练习4:文本文件中存储了多个文章标题、作者,标题和作者之间用若干空格(数量不定)隔开,每行一个,标题有的长有的短,输出到控制台的时候最多标题长度20,如果超过20,则截取长度17的子串并且最后添加“...”,加一个竖线后输出作者的名字。 练习5:从ini格式的文件中(每行是“键=值”格式)中读取出配置项的值。编写一个函数来读这些文件:读取指定文件的某个配置项的值。string GetConfigValue(string filename,string itemName) 练习6:自己动手写聊天机器人,能够回答不同城市的天气、回答感情问题、问的次数过多还会饿死,提问可以模糊提问(包含指定关键词)。问“天气:北京”就回复“北京的天气是晴”。
  • 40. 函数的ref、out参数(*)函数参数默认是值传递的,也就是“复制一份”,例子: int age=20; IncAge(age); Console.WriteLine("age={0}",age); ref必须先初始化,因为是引用,所以必须先“有”,才能引用,而out则是内部为外部赋值,所以不需要初始化,而且外部初始化也没用。 ref应用场景内部对外部的值进行改变,out则是内部为外部变量赋值,out一般用在函数有多个返回值的场所。 案例:两个变量的交换;int.TryParse。
  • 41. 面向对象概念(*)面向对象不是取代面向过程的。 类、对象。“人”是类,“张三”是“人”这个类的对象。类是抽象的,对象是具体的。按钮就是类,某个按钮就是对象。对象可以叫做类的实例(Instance)。类就像int,对象就像10。字段Field(和某个对象相关的变量),字段就是类的状态。人这个类有姓名、年龄、身高等字段。类不占内存,对象才占内存。 方法Method,方法就是类能够执行的动作,比如问好、吃饭等。 类的继承,类之间可以有继承关系,比如“电脑”类可以从“电器”类继承,这样的好处是“电脑”类只需要定义自己特有的字段、方法就可以,也就是只要定义内存大小、CPU型号这些字段或者弹出光驱等方法就可以。父类(Parent)、基类(Base,基业,祖宗十八代传下来的)。电脑类是电器类的子类(ChildClass)。重用。 面向对象的三个特性:封装、继承、多态。 没有面向对象的世界中的难题。
  • 42. 定义类class Person{ }定义方法(类的函数): class Person { public void SayHello() { Console.WriteLine("你好,我是{0}",this.Name); //不写this.也可以,写上更清晰 } } 初始化对象,调用方法: Person tom = new Person(); tom.SayHello(); 对象必须调用构造函数初始化“new Person()”后才能用,不能Person tom这样声明;就调用。定义字段: class Person { public string Name; public int Age; public void SayHello() { Console.WriteLine("你好,我是{0}",Name); } } 初始化对象,调用方法: Person tom = new Person(); tom.Name="tom"; tom.SayHello(); Console.WiteLine("{0}",tome.Name)一个类可有有多个实例。 类就是把一系列相关的变量(状态)、行为定义为一个整体。字段记录的就是这个对象相关的数据。
  • 43. 成员访问级别字段、方法、属性(后面讲)都可以叫做类的成员Member,它们都需要定义访问级别。访问级别的用处在于控制成员在哪些地方可以被访问,这样达到面向对象中“封装”的目的。 几个访问级别:public(任何地方都可以访问);private(默认级别。只能由本类中的成员访问)。还有internal、protected两个级别,以后会讲。 class Person { private string Name; public void GiveName(string name) { Name = name;//拒绝不好听的名字 } public void SayHello() { Console.WriteLine("你好,我是{0}",Name); } } Person tom = new Person(); tom.GiveName("tom"); //tom.Name="tom"; tom.SayHello(); 永远不要把字段public
  • 44. 属性惯用法:属性开头字母大写,字段开头字母小写 class Person { private int age; public int Age { get{return age;} set{age=value;} } public void SayHello() { Console.WriteLine("我的年龄是{0}",Age); } }只用set或者只用get就可以定义只读或者只写属性(只写的不常见) 可以为set、get设置访问级别 例子,限制非法值的设置 (.Net3.x)简化set、get:public int Age{get;set;}。适合于set、get中没有特殊逻辑代码的情况。允许外部访问的值一定要声明为属性。 字段和属性的区别是什么?属性看似字段、不是字段,可以进行非法值控制,可以设置只读。 set、get块内部其实就是get_***、set_***方法。
  • 45. 课上练习面向对象版聊天机器人 机器人有不同的名字、维护自己的FullLevel,可以SayHello(我叫***),可以喂食(Eat(int foodCount)),可以对它说话(Speak),对异常情况(错误的喂饭数字,喂的太多撑死了)进行处理,有两个机器人供选择,一开始通过1、2数字选择聊天机器人。
  • 46. 构造函数构造函数用来创建对象,并且可以在构造函数中对对象进行初始化。 构造函数是用来创建对象的特殊函数,函数名和类名一样,没有返回值,连void都不用。 构造函数可以有参数,new对象的时候传递函数参数即可 构造函数可以重载,也就是有多个参数不同的构造函数。 如果不指定构造函数,则类有一个默认的无参构造函数。如果指定了构造函数,则不再有默认的无参构造函数,如果需要无参构造函数,则需要自己来写。
  • 47. 对象的引用(非常重要)i1=3;i2=i1;i1++;//i2是3 p1=new Person();p1.i=3;p2=p1;p1.i++;//p2.i是4 int、string、decimal、bool、byte等基础类型(值类型)是传递拷贝;对象(引用类型)则是传递引用。因为基础类型不怎么占内存,而对象则比较占内存。 函数间传递对象。 为对象变量重新赋值。p2=p1是让p2指向p1指向的对象。
  • 48. 继承public class Chinese:Person { public string HuKou{get;set;} public void KongFu(){....} } Chinese p1 = new Chinese(); p1.Name="李雷"; p1.HuKou="北京市朝阳区"; p1.SayHello(); p1.KongFu();定义类的时候不指定父类,则父类是Object类。Object类是任何类的直接或者间接父类。
  • 49. 对象的隐式转换和显式转换Chinese ch= new Chinese(); //隐式转换,把子类变量赋值给父类变量 Person p = ch; //显式转换,把父类变量赋值给子类变量 Person p = new Chinese(); Chinese ch = (Chinese)p; //如果对象不在同一个继承树路径上 //则不能强制类型转换 Dog g = new Dog(); Chinese ch = (Chinese)g;//错误 //is运算 if(p is Chinese) { Console.WriteLine("中国人"); } else if(p is Korean) { Console.WriteLine("韩国人"); }//as 运算符 Chinese ch = p as Chinese ; if(ch!=null) { Console.WriteLine("中国人"); } Korean ch = p as Korean ; if(ch!=null) { Console.WriteLine("韩国人"); } ()转换和as 转换的区别:如果转换失败()会报异常,而as则会返回null。
  • 50. 异常与异常处理传统的错误表示方式:错误码。举例。需要知道不同错误码的含义,如果不处理错误码,则程序可能陷入不可以预置的错误。陈摄影师以为文件已经被删除造成的麻烦。 错误码的缺点:不处理则很难发现,每次处理则很麻烦;难以看出错误的原因;容易使得程序进入不确定状态。 try catch。Exception ex 异常也是对象。 Exception 类主要属性:Message、StackTrace 发生异常后程序默认就退出了,try代码块中的后续代码不会被执行。catch以后的代码则会继续执行。 不要吃掉异常,一般情况下不需要处理异常。 扔出自己的异常,扔:throw,抓住:catch
  • 51. 常量与静态成员const常量。常量名要大写。一定不会变化的值才能声明为常量。 全局变量。static类变量。 不用new就能用的方法:static方法,static方法其实就是普通函数 在static方法中可以调用其他static成员,但是不能调用非static成员。在非static方法中可以调用static成员。 静态类,不能被new的类就是静态类。静态类一般用来实现一些函数库。***Helper,SqlHelper,PageHelper。
  • 52. 命名空间namespace(命名空间),用于解决类重名问题,可以看做“类的文件夹”。 在代码中使用其他类的时候需要using类所在的namespace。System.Collections.ArrayList,快速引入的方法,右键→解析。 为什么使用Convert、Console等类不需要自己写using? 如果代码和被使用的类在一个namespace则不需要using。 可以修改默认的namespace,因此不要认为在相同文件夹下就不用using,不在相同文件夹下就需要using。
  • 53. 索引器C#中提供了按照索引器进行访问的方法 定义索引器的方式:string this[int index]{get { return ""; }set { }},string为索引器的类型,[]中是参数列表。进行索引器写操作就是调用set代码块,在set内部使用value得到用户设置的值;进行读操作就执行get代码块。 索引器参数可以不止一个,类型也不限于int,几乎可以是任意类型。
  • 54. 复习复习上周知识点、难点
  • 55. 第一个Windows程序WinForm:Windows Form,.Net中用来开发Windows窗口程序的技术,无论是之前学的控制台程序,还是后面要学的ASP.Net都是调用.Net框架,因此所有知识点都是一样的。 新建一个Windows项目:Windows→Windows窗体应用程序 控件:窗口上很多元素都是相似的,因此将这些元素抽象为一些类,这些类就叫做控件。识别PowerPoint中的控件,按钮(Button)、文本框(TextBox)、标签(Label)、单选按钮(RadioButton)、复选框(CheckBox)。 添加、删除、移动、缩放控件
  • 56. WinForm概念拖放控件,输入姓名,点击按钮,窗口标题显示问好。设置窗口对象的属性就可以改变窗口的外观。 点击按钮调用TextBox的Hide方法,调用控件的方法就可以使得控件发生动作。 当用户点击按钮的时候Button1_click方法被调用,这个方法不是程序员调用的,而是程序员把方法写好,并且说明“当用户点击按钮的时候执行Button1_click方法中的代码”,这一点和控制台程序不同。这被称为“好莱坞原则”:不要找我,我会找你(Don't call me,I will call you ) 控件、属性、事件、事件处理方法、控件的名字(控件的实例;对象名)
  • 57. 简单的WinForm程序简单的加法计算器,用户在文本框1、2中输入两个数,点击按钮,在文本框3中显示两个数的和。如果1或者2为错误的数据格式,则弹出对话框提示错误。int.TryParse、MessageBox.Show。 string s = string.Format("{0}你好", textBox1.Text);//推荐 练习1:输入宽和高,输出面积。 练习2:输入Email地址,输出用户名和域名。 练习3:用户在文本框1、2中输入两个数,点击按钮,在文本框3中显示从文本框1中的数字到文本框2中数字之间的累加和。如果1或者2为错误的数据格式,则弹出对话框提示错误。如果文本框1中的数字比文本框2中数字大,则提示错误。 练习4:页面上有一张图片(PictureBox,在Image属性中加载图片),默认是隐藏的(Visible=False),用户在文本框中输入身份证号(131226198105223452),点击按钮,如果年龄大于18岁则显示图片(Visible=True),否则提示年龄太小。取当前年份:DateTime.Now.Year。 练习5:页面上有一个文本框,文本框左侧和右侧各有一个按钮,点击左侧按钮文本框中的文字向左循环滚动一次,点击右侧按钮文本框中的文字向右循环滚动一次。
  • 58. TextBox文本框的几种模式:Multiline(多行)、PasswordChar(密码) 将文本框的PasswordChar设为*就是密码框效果,将MultiLine属性设置为true并且将高度拉到合适的大小就是多行效果,textBox4.AppendText("hello"+"\n")就是附加一行。 控件名要有含义、控件名前缀的“潜规则”。按钮Button:btn;文本框TextBox:txt;复选框CheckBox:cb。控件的名字要有意义。 案例1:登录界面。登录错误三次退出程序,假设用户名、密码是admin、888888,不区分大小写。(易错点:局部变量与类变量) 退出程序this.Close()或者Application.Exit() 案例2:修改密码。界面上有旧密码、新密码、重复新密码,假设旧密码为888888,两次输入的新密码必须和旧密码不一样,并且两次输入的新密码必须一致。 案例3:在多行文本框中输入多行“姓名=成绩”格式的数据,要求输出成绩最高的学生的姓名和成绩。
  • 59. ComboBoxSelectedIndex :选中项的序号。没有任何选中的时候是-1,否则是选中的序号(0开始) 练习1:简单的四则运算器 如何禁止用户编辑?三种风格。 响应选择改变事件 练习2:省市选择器 练习3:日月选择器,假设2月份总是28天。1、3、5、7、8、10、12月份是31天,其他是30天。表驱动。
  • 60. ListBoxListBox:SelectedIndex、Items、SelectedIndexChanged事件。 多选的方式,设置SelectionMode为MultiExtend ListBox:SelectedIndices、SelectedItem、SelectedItems、SelectionMode; 案例:人员选择,左边选择到右边、右边退回左边、批量添加。遇到的问题,删除顺序,计算机的思维。 问题:删除自动生成的事件代码。先在事件视图中删除方法名,再到代码中删除;先删除form.cs中的,再去手动删除designer.cs中。
  • 61. 计时器TimerTimer。每隔一段时间触发一个事件。不可视控件。Inerval、Enabled。Tick事件。 计量单位:ms(毫秒)。 1秒=1000毫秒 DateTime 案例:小时钟。取当前时间DateTime.Now.ToString(); 案例:走马灯 案例:QQ消息窗口。如何显示其他窗口。
  • 62. 右下角提示信息窗口Windows坐标系:左上角为原点;窗口的Left值为窗口左上角的横坐标,Top值为窗口左上角的纵坐标;窗口的Width为宽度,Width为高度。 取得屏幕工作区Screen.GetWorkingArea(this) 将窗口显示在右下角,简单的数学运算。
  • 63. 滑动提示窗口创建一个Timer,每隔一段时间修改一下Top的值,当全部显示出来的时候禁用Timer。 对外提供提供SlideShow(String caption,String msg)方法 超时自动关闭。 滑动隐藏。Timer接力。 鼠标点击则取消“超时自动隐藏”。
  • 64. 树状结构数据
  • 65. TreeView控件树的基本概念:父节点、子节点、兄弟节点、根节点 编辑节点,节点名字Name,节点文字Text 动态添加节点(VS编辑界面中有增加根节点、增加子节点两个按钮): 向根节点下增加子节点:treeView.Nodes.Add,它的返回值就是创建的节点对象。treeView.Nodes代表根节点的所有子节点。 向TreeNode增加子节点,treeNode.Nodes.Add,它的返回值就是创建的节点对象。treeNode.Nodes代表节点的所有子节点。
  • 66. 练习:构建省市县三级树首先treeView.Nodes.Add添加省节点。并且把添加的节点TreeNode对象放到treeNodeLiaoning等变量中 向treeNodeLiaoning等省级节点下添加市节点,并且把添加的节点TreeNode对象放到treeNodeShenYang等变量中 向treeNodeShenYang等市节点下增加区县节点。
  • 67. TreeView深入选择项发生变化的时候在TextBox中显示当前选择项的值。AfterSelect事件。 TreeNode的Tag,TreeNode中Text只能盛放显示的值,可以用Tag属性给节点关联一个对象。 Tag属性是Object类型的,因此可以关联任何的对象。案例:省市县显示当前项的邮编 练习:选择节点的时候显示市长、人口(int)类型。
  • 68. 容器控件GroupBox Panel TabControl(增删Tab页,设定激活的页)
  • 69. 其他常用控件RadioButton:Checked。CheckedChanged和Click事件的区别 CheckBox CheckedListBox DateTimePicker。 PictureBox 作业:开发注册页面。数据合法性判断:Email、密码强度实时显示。带协议、同意协议CheckBox。
  • 70. 文件对话框打开文件对话框 OpenFileDialog 两种创建方式:可视化拖放、new 显示对话框的方式:ShowDialog ShowDialog的返回值DialogResult类型 通过FileName属性得到选择的文件名 属性:Title、InitialDirectory 文件过滤器 Filter:文本文件|*.txt|All|*.* SaveFileDialog。OpenFileDialog相同的成员:Title、ShowDialog、FileName等
  • 71. 布局绝对坐标定位的缺点。 如何禁止窗口缩放。MaxmizeBox=false,FormBorderStyle=FixedDialog。 Anchor 几种经典的布局:记事本、左边一个固定的多行TextBox右边一个填充的TextBox
  • 72. 列表(非范型)数组的局限性:无法对数据中的数据进行动态的增删。 ArrayList(列表)。Add、Clear、Contains、Count、IndexOf、Insert、Remove、RemoveAt、Reverse、Sort、索引器。 作业1:输入整数,然后反序输出 作业2:两个列表的连接、合并。 作业3:分拣奇偶数,奇数在左,偶数在右,面试题
  • 73. Hashtable简繁体翻译,为什么效率这么高 HashSet
  • 74. 范型用ArrayList的麻烦的地方:数据放进去就不知道是什么类型的了;不能防止非法类型数据的放入;将ArrayList返回给其他函数,会令调用者很困惑。 List 除此除外并无不同。 IEnumerable、ICollection 除了List类外,还有很多类支持范型,比如Dictionary等,待定的类型还可以不止一个。简繁体翻译器。
  • 75. DictionaryKey-value Pair 键值对 作业:Dictionary性能测试 Dictionary: Add:添加,如果重复,则报错 索引器:可以重复设置,即使不存在也没关系,如果重复则保留最后一次的值 ContainsKey,判断是否存在这个Key
  • 76. 自定义对话框
  • 77. 对话框、字符串、数组综合案例选择成绩文件。计算平均分,查找某个学生的成绩。File.ReadAllLines
  • 78. 菜单、工具栏主菜单(MenuStrip):分割线、快捷键、图标、子菜单、事件响应。 右键菜单(ContextMenuStrip) 工具栏ToolStrip 状态栏 StatusStrip
  • 79. 菜单工具栏案例案例:自己动手写记事本。打开、保存、另存为、退出、剪切、复制、粘贴 带工具栏 练习:标题显示文件名 练习:状态栏中显示当前时间
  • 80. windows编程基础
  • 81. 调试(*理解)Debug暂停(不知道程序现在运行到哪里了) 断点、设置断点 breakpoint 条件断点 命中次数断点 查看变量的值,查看表达式的值。红色、黑色
  • 82. 反编译器讲一点面向对象以后讲正则表达式。
  • 83. 变量作用域变量名:变量名就像试验实例容器的编号,在一个实验室中,编号不能重复。如果去了更高一级的实验室,就不能和下属的实验室的容易编号重复。只要不出实验室,不同实验室之间的容器编号可以重复。 static void Main(string[] args) { string name = "tom"; SayHello(); } static void SayHello() { Console.WriteLine("我的姓名是:{0}",name); } static void Main(string[] args) { string name = "tom"; SayHello(); } static void SayHello() { string name = "jerry"; Console.WriteLine("我的姓名是:{0}",name); }
  • 84. 变量作用域2 string name = "tom"; if (name == "tom") { string name = "jerry"; } for (int i = 0; i < 10; i++) { string name = i.ToString(); } Console.WriteLine("{0}",name); for (int i = 0; i < 10; i++) { string name = i.ToString(); } Console.WriteLine("{0}",i); int i; for (i = 0; i < 10; i++) { string name = i.ToString(); } Console.WriteLine("{0}",i); static void SayHello(string name) { string name = "lily"; Console.WriteLine("我是{0}",name); }在同一个括号内变量定义不能重名,括号可以嵌套,但是通过函数的调用并不在这个范围内 int i = 3; if (i > 3) { if (i < 100) { int i = 10; } } if (s=="a") { int i = 0; } if (s=="b") { int i = 0; }