《.NET 软件工程师就业求职手册》 - 书摘精要

(前言) 作为一名.NET技术开发人员,只要基础扎实,完全可以通过不断学习,轻松游走于各个 .NET 应用领域。

(P6)

经验丰富的应聘者,其简历往往只有一页。

在受教育经历方面,只需要填写最高层次的受教育经历或培训即可,不要将简历写得像档案一样繁琐。

专业经验对于计算机方面的岗位非常重要。

(P7) 如果应聘者已经有过工作经验,则一定要给出曾经工作的详细情况,以及完成项目的详细情况,使用人企业迅速判断应聘者的能力。

(P8) 如果应聘者有工作经验,用人企业看重的是应聘者曾经工作的具体细节,而不是跳槽次数。所以应聘者不需要列举太多的工作经历。作为IT技术方面的岗位,应聘者应注明自己的技术博客,作为自己技术实力的展示,最后应将自己曾经参与的项目做详细描述。

(P9) 应聘者要主动获取有关用人企业的信息,了解企业的性质、规模、业务信息以及企业文化等。

(P11) 算法是程序设计的核心之一,高效率的程序必然有良好的算法支持。针对不同问题,算法虽然有多种,但面试中只会包含比较常见的,和工作岗位密切相关的算法题目。

(P14) 社会处在高速发展阶段,“物竞天择,适者生存”,凡事“预则立,不预则废”。

(P15) 20 - 30 岁年龄段成为职业生涯的黄金期,人生的冲刺阶段。如果个人在这段时期没有做好完善的职业规划,或者没有将其有效地实施,则其发展将颇为坎坷。

(P18) 罗马不是一天建成的,要实现自己的职业梦想,必须积累足够的实力和经验。为了完成这些积累,必须选择适合自己的发展平台。

(P19)

计算机编程语言技术无所谓好坏,职业规划不应该以编程语言或技术平台为主线进行设计,而应当根据个人所适合的技术应用方向去进行深入的学习和实践,直至成为专家。懂多种技术不如精通某种技术。

对于软件行业,编程的技术是核心竞争力。

(P23) 类通过构造函数生成对象。

(P25) 类是用于描述对象的特征、状态和行为的模板。

(P26) 某些时候需要访问私有类成员,可通过 Get 和 Set 访问器读取。

(P28) C# 默认的类访问修饰符为 internal

(P29) 即使派生类和基类在不同的程序集中,派生类仍可访问基类的protected 修饰符成员。

(P31) 属性提供了比较灵活的数据访问方法,编写代码时注意显式声明的 Set 访问符必须比属性修饰符更严格。当 Get 或 Set 访问器没有显式访问修饰符时,其默认访问限制和属性一致。

(P33)

sealed 修饰符用于修饰类、实例方法和属性;

sealed 修饰符和 abstract 修饰符是相互排斥的,无法共存;

sealed 修饰实例方法或属性时,必须和 override 一起使用;

(P35)

当类中某些成员不需要创建实例实现,则可将其声明为静态成员;

类中没有和对象实例相关的成员,即类体中只有静态成员时,可以声明该类为静态类。静态类无法用“new”创建对象,所以不能编写构造函数,并且该类是密封类(既无法被继承)。

声明静态类时,必须保证其内含成员全部为静态成员;

(P37)

没有参数的构造函数被称为默认构造函数,如果非静态类的类体中没有声明构造函数,类将自动提供一个默认构造函数,并将类成员初始化为默认值;

结构类型 (Struct) 是值类型,不需要显式声明默认构造函数,编译器将自动生成默认构造函数。当用 (new) 运算符实例化时默认构造函数才被调用,并将成员初始化为默认值;

静态构造函数在创建实例前或引用静态成员前自动调用,一般用于对静态成员的操作。

私有的默认构造函数,可以阻止类在外部创建类的实例。

(P39)

函数重载 —— 给函数定义不同的参数个数或不同的参数类型,可以声明不同的同名函数(返回值也可不同);

派生类中只有继承的虚方法或抽象方法可以被重写,而静态方法不能被重写;

(P40) 派生类所继承的非密封重写方法(即 override 方法)也可以重写,因为该方法是被重写过的。

(P43)

接口与抽象类的主要区别:

1. 抽象类只能派生类,而接口可以派生类和结构;

2. 抽象类的派生类可以是抽象类,即使抽象成员在派生类中不一定被完全实现。而接口要求其派生类结构必须完全实现其成员;

3. 抽象类可以包含已经实现的成员,可以包含字段。而接口只包含未实现的成员,不能包含字段,并且接口及所含成员必须为 public 访问级别。

4. 类只能继承一个抽象类,但可以继承(实现)多个接口。

(P45)

抽象方法的属性是隐性的 virtual ,所以派生类实现抽象方法或属性必须使用 override 关键字;

抽象类的抽象成员不能使用 virtual 或 static 修饰;

(P51)

“this”:用于引用类的当前实例;

“base”:用于派生类访问基类成员;

(P53)

静态成员和实例无关,所以静态成员中不能使用 this 关键字;

this 仅限于构造函数和方法成员中使用;

base 关键字访问基类的成员时,必须保持基类成员有相应的访问权限;

(P53) 索引器可以使客户程序很方便地访问类中集合或数组,访问方法类似于通过索引访问数组,并且索引器向客户程序隐藏了内部的数据结构;

(P57) 索引器的访问器不能添加修饰符;

(P58)

ASP.NET 在首次执行时进行编译,编译后的程序遇到请求可以直接运行;

ASP.NET 还提供了预编译功能,可以在部署网站之前先进行编译,预编译可以改进首次请求网站的性能;

ASP.NET 就是网页版的 .NET 应用程序;

(P59) ActiveX Data Object (ADO) 是 ASP 内置的组件,其操作的数据源不局限于数据库,还可以是其它数据表,例如 Excel 、文本文件等,即 ODBC 能存取的所有数据源;

(P60)

ADO.NET 核心部分是 .NET Data Provider 和 DataSet 对象。 前者被称为数据提供者,后者被称为数据结果集对象。 .NET Data Provider 包括 Connection、 Command、DataReader 和 DataAdapter 这四种对象。

使用 ADO.NET 需要引用相应的命名空间,不同的数据库,引用不同的命名空间,但是都需要引用共同的命名空间 Syste.Data;

(P61)

.NET 程序集是自我描述的安装单元,程序集是一个逻辑单元,而非一个文件。程序集可以包含元数据的多个文件,也可以是一个 DLL 或 EXE 文件。程序集作为 .NET 可执行程序或 .NET 可执行程序的一部分,包含了程序的文件集合资源文件。

程序集分为私有程序集和共享程序集,私有程序集是创建 .NET 项目时默认的,也是比较常用的方式。私有程序集以可执行文件或库的形式提供应用程序,库中的代码只服务于这个应用程序。而共享程序集是一个公共库,服务于系统中所有程序。共享程序集必须安装到 .NET 的指定目录中,而其它被服务的程序不需要知道安装的地址。

任何 .NET 程序均于程序集构成,程序集是包含已编译的面向 .NET Framework 代码的逻辑单元。程序集包含描述自身的元数据,这种元数据位于程序集清单中,用于检查版本以及自身的完整性。

动态程序集位于内存中,而非存储于文件中。

应用程序域是 .NET 中程序的“边界”。相对于进程边界,应用程序域边界范围更小。使用应用程序域可分离组件,并且不会导致类似于进程的性能问题。

进程有独立的虚拟内存,以保证进程之间的内存无法互写。

一个进程可以容纳多个应用程序域,在没有代理的情况下,不同的应用程序域中的实例和静态成员无法共享,这样做保证了安全性。

(P65)

中间语言采用即时编译,也称为 JIT 编译,这种编译方式只编译调用的代码,而不是所有的代码编译过的部分将被存储在内存中,再执行时不需要重复编译。退出程序时,已编译的代码才会被清除。

.NET 的 CLR 和 JVM、AVM 是类似的;

(P69) .NET Framework 的文件形式主要由公共语言进行时 (CLR) 和 基类库 (BCL) 组成,前者提供进行库环境,而后者提供丰富的类库,适用于全部 .NET 编译语言编写的托管代码调用。

(P70) 命名空间只是 .NET 组织各种相关类型的逻辑形式。

(P71) C# 的数据类型分为值类型和引用类型,值类型变量包含数据,而引用类型变量只包含数据的内存地址。值类型离开其定义的作用域,将被从内存中清除,而引用类型引用的对象一直存留在托管堆, .NET 收集器自动将其销毁。

(P72) 值类型变量作为函数参数传递,只是传递其副本;引用类型变量作为函数参数传递,将传递数据引用,函数体对引用的操作将改变该数据的值。

(P73)

CTS 中所有类型都是对象,其共同的基类为 System.Object;

CTS 的值类型可分为简单类型、枚举类型和结构类型,而引用类型则分为类类型、数组类型、接口类型和委托类型。并且值类型是密封的,不能派生其它类型,必须继承 System.Value 。相反,引用类型可以继承除 System.Value 以外的任何非封装类型。

(P73)

C# 的装箱是创建引用类型变量保存值类型变量值,而拆箱是装箱的逆向操作,即将引用类型的值转换为值类型变量的值。

装箱的过程实际是创建了一个新对象,将值类型变量在堆栈的数据值复制到托管堆的新对象上,并由对象类型的变量所引用。拆箱的过程是在堆栈上创建新的值类型的变量,并把托管堆上的对象存储的数据值复制到新的值类型变量。

不过在拆箱的过程中,须保证值类型的数据类型和托管堆对应值的数据类型保持一致,否则拆箱过程将产生异常。

(P75) 使用 Enum 类的 GetValue()方法,返回 System.Array 类的实例;

(P79)

结构可以声明带参数的构造函数,其使用方法和类一致;

值类型变量一旦超出作用域即被销毁,而引用类型由内存垃圾处理机制完成收集。

(P81)

如果没有修饰符则按值传递参数;

“out” —— 表示引用传递参数,但函数必须将其赋值;

“params” —— 表示形参为不去定个数的一组实参,这组实参必须具有相同数据类型;

“ref” —— 表示按引用传递参数,实参传递前需要赋初始值,但在函数中可以不被赋值;

(P84)

实例和静态方法使用参数修饰符无区别;

C# 3.0 提供了 var 关键字,用于隐式声明局部变量的数据类型,由编译器根据初始值推测具体的数据类型。

(P88) 将值类型加上“?”后缀即可声明这种特殊的可空类型变量,其对应的数据范围是原值类型的底层类型范围加上 null 值;

(P90) C# 3.0 提供的扩展方法用于扩展指定类型的功能,而不修改类型内部的代码,并且方法可以单独定义在外部程序集。

(P93)

1. 扩展方法所属类必须为静态非泛型类,即扩展方法也是静态方法;

2. 扩展方法的第一个参数为被扩展的类型实例,并且必须使用 this 进行修饰;

3. 扩展方法从第2个参数开始对应被扩展类型实例所传递的参数列表,即扩展类型实例传递的第1个参数对应扩展方法定义的第2个参数,依此类推;

4. 被扩展类型实例可像调用类型内部定义的实例方法一样调用扩展方法。

(P95)

C# 3.0 提供的对象构造器,可以非常灵活地初始化对象成员,并且无须定义过多的重载构造桉函数。

C# 3.0 可以通过 var 关键字和对象构造器直接定义没有名称(编译器分配名称)的类,同时创建并初始化类成员。匿名类型直接派生于 System.Object 类,并且重写了3个方法,分别为: Equals()方法、GetHashCode()方法和 ToString()方法;

(P97)

匿名类型的名称在程序中无法访问;

匿名类型在编译后仍然是一个普通的密封类(不可派生其它类),只是名称由编译器分配;

(P100)

分部方法可以是静态方法,但必须是隐式的私有方法,并且是无返回值的方法;

分部方法只能将方法分为两部分,即声明部分和实现部分;

分部方法只用于分部类型,方法的声明部分和实现部分;

分部方法可以有 ref 参数,但不能有 out 参数;

不允许将委托转换为分部方法;

(P103) 用 Viual Studio 2005 / 2008 创建的项目,其属性默认声明了 Debug 和 Trace 等号;

(P103)

栈指堆栈,堆指托管堆;

堆栈用于存储非实例成员的值类型数据,以及引用类型的变量(用于存储引用类型实例)

托管堆用于存储引用类型实例的数据及相关信息;

(P104)

堆栈从内存地址高位开始存储数据;

托管堆从内存地址低位开始存数数据;

(P105)

在常见的 32 位 Windows 操作系统中,单个进程的寻址能力为4GB;

Windows 操作系统通过虚拟寻址系统管理数据在内存中存储方式,虚拟寻址将持续的内存地址转化为物理内存的实际地址;

操作系统常常将物理内存和虚拟内存配合使用。在程序开发中,只需要将其看做一块连续的内存空间即可;

(P106)

生命周期越短的对象(新创建的对象)代数越小,反之代数越大。

第2代对象被检查后仍然是第2代,不会继续升级了;

垃圾收集器回收时,当前程序进程的所有活动线程将挂起;

(P108) GC 类的 WaitForPendingFinalizers() 方法,该方法挂起当前线程直到所有对象被终结,所以一般用在 Collect() 方法之后;

(P112)

System.Object 类中析构函数代码如下所示:

protected virtual void Finalize() {}

(P113) Dispose() 方法不仅可以清理非托管资源的代码,还可以与其它托管对象通信。因为 Dispose() 是显式调用,所以开发者可以自己把握 Dispose() 方法调用的时机而不需要担心其他托管对象是否已被自动销毁。显式调用 Dispose() 方法可以在非托管资源用完后马上将其清理,相比析构函数更加有效。

(P112)

Suppress Finalize() 方法通知垃圾回收器该对象不需要被终结,即避免了垃圾收集器再次调用析构函数;

由于结构为值类型,所以无法使用析构函数;

重写析构函数不能使用 override 修饰符,而是使用“~类名称()”

如果 CLR 检测到对象重写了默认析构函数,将会把对象标记为可终结对象,并把对象的地址引用保存在垃圾收集器管理的终结队列中。在将要发生回收时,将终结队列所指的对象复制到终结对象列表中,第1次回收时调用析构函数,不会删除对象,只有在第2次回收时才真正删除对象;

(P120)

没有异常类型参数的 catch 代码块一般很少使用,如果使用时应放在最后;

没有参数的 catch 代码块,处理 C# 以外的语言或非托管代码抛出的异常类型;

(P121) Data 属性从 System.Exception 类中继承而来的属性,用于存储“名称/值”对;

(P123) 在.NET程序的各种异常类型中,基类库所定义的异常由 CLR 创建并抛出异常,这种异常被称为系统级异常,系统级异常共有的基类为 System.SystemException 。为了和系统级异常进行区别,自定义异常类应继承于 System.ApplicationException 类,这种异常被称为应用程序异常;

(P127)

“==”运算在子没有重载的情况下,比较的是对象引用;

System.Object 类提供了3种方法比较引用类型是否相等,分别为虚拟版本的 Equals()方法、静态 Equals()方法和静态Reference.Equals()方法;

System.Object类定义的3种方法都是用于比较两个对象是否指向堆上相同对象,并且比较的是引用地址,如果相等则返回 true;

静态的 Reference.Equals()方法接收两个 object 参数,如果两个引用类型引用均为 null 时,结果为 true;

用 Reference.Equals()方法比较2个值类型变量毫无意义,结果肯定是 False,即使是2个值相等的变量。因为在 Reference.Equals() 方法比较前,被比较的值类型变量将会被装箱操作,隐性地创建2个不同对象,所以其地址引用也将不同;

(P128) 虚拟的 Equals()方法是实例方法,它由实例直接调用并接收一个 object 参数,这个参数同样用于比较引用类型的引用地址是否相等。其派生类一般将其重写为比较对象的状态值,即基于值的引用;

(P128)

表示某个值或一组值的任何类都应该重写 Equals()方法。如果类型要实现 IComparable 接口, 则它同样应该重写 Equals() 方法;

静态的Equals()方法和虚拟的Equals()方法一样,只是静态调用时接收两个 object 参数,使用时调用实例 Equals()方法。所以当虚拟 Equals()方法被重写为基于值的相等比较时,该方法相当于被重写;

未重载“==”运算符的引用类型,“==”运算符用于比较两个引用类型的引用地址,跟引用类型的 Equals()方法一致。所以“==”运算符也被称为第4种判断相等性的方法;

(P133)

StreamWriter 对象名称 = new StremWriter(文件路径);

StreamReader 对象名称 = new StreamReader(文件路径, 是否追加内容, 字符编码);

StreamWriter 类和 StreamReader 类的对象使用后,调用 Close()方法关闭,完成文件数据更新;

File 类也提供了静态方法提供类似的功能,如果只需要一次性将字符串写入文件,File 类的静态方法 WriteAllText() 更为简便, WriteAllText() 方法常用的调用方式如以下代码所示:

File.WriteAllText(文件路径, 字符串内容, 字符编码);

此方法编写较为简单,功能和 StreamWriter 对象类似,可以用 File 类的静态方法 ReadAllText()的常用调用方式读取,如以下代码所示:

File.ReadAllText(文件路径, 字符编码);

字符编码是将字节和字符的格式转换规范;

UTF-8 编码 是国际文本信息交换的主要方法,它可以支持世界上的所有语言,在实际应用中为了使文件使用更广泛,建议采用 UTF-8 编码;

(P136) File 类有部分独特的成员,提供更简便的文件操作;

(P138) 复制文件则可以直接使用 File 类的 Copy()静态方法:

File.Copy(原文件路径, 目标路径 + Path.GetFileName(原文件路径), 是否覆盖);

(P140) System.IO 命名空间提供了 FileSystemWatcher 类,用于监视(观察)所指定的目录下文件及子目录的变化;

(P141) FileSystemWatcher 类可以监视本地计算机、网络驱动器或远程计算机上的文件;

(P144) 异常处理语句结构是大型程序中容易遗漏的部分,读者应保持添加异常处理的习惯;

(P146)

// Ienumerable 接口的成员

IEnumerator GetEnumerator();

// IEnumerator 接口的成员

bool MoveNext();

object Current {get;}

void Reset();

(P147)

迭代器方法只需要在类型中直接定义一个类似的 GetEnumerator()方法,使用 foreach 语句遍历集合,并用 yield return 返回每个子项;

迭代器方法不需要显式实现2个接口。实际上 IEnumerable 接口和 IEnumerator 接口被迭代器方法隐藏实现,使用时不需要关心如何实现。

(P151)

需要对集合类型的子项按指定的键值排序,可以用实现System.IComparable 接口的 CompareTo()方法完成;

如果集合类型的子项是自定义类型的对象,必须在自定义中实现 System.IComprable 接口的 CompareTo()方法,才能完成排序的功能;

(P152)

使用“.”运算符连接接口名称和所需要实现的方法名称,以显式方式实现接口方法,可以有效地避免方法重名等问题。

如果集合类型的子项需要比较多个键值(相对于对象的多个属性或其他值),就需要定义一个实现 System.Collections.IComparer 接口 Compare()方法的辅助类;

利用 Sort()方法的重载版本,可以根据不同情况,灵活地对数组子项进行不同键值的排序;

IComparable 接口的命名空间是 System ,而 IComparer 接口命名空间是 System.Collections;

(P157)

Array 类在 System命名空间下, ArrayList 在 Syste.Collections 命名空间下;

使用默认构造函数创建的 ArrayList 类对象默认初始值容量为16;

ArrayList 类还提供了 ToArray()方法,用于将 ArrayList 内容转换为 object 类型的数组并返回;

(P165)

class MyClass<T>

{

T 字段名称;

T 属性名称 {get; set;}

T 方法名称 (T 参数列表)
}

(P168) System.Collections 命名空间下的集合类型在 System.Collections.Generic 命名空间有相应的泛型版本;

(P171) “default”关键字在泛型代码中用于设置类型占位符的默认值: 变量 = default(T);

(P181) “delegate”关键字定义时,临时定义了一个派生于 System.MulticastDelegate 类的密封类,这个类与基类 System.Delegate 均同为委托提供必要的基础成员;

(P183) 多点委托的委托类型必须保证相同。另外,多点委托所引用的多个方法都有返回值的情况下,只有最后被调用的方法才有返回值;

(P184) “+=”运算符和“-=”运算符被重载,编译时这2个运算符分别转换为调用 Delegate 类的 Combine()静态方法和 Remove()静态方法;

(P186)

必须理解事件和委托的联系,才能掌握事件机制的本质;

事件就是当对象或类(发布者)状态发生改变时,对象或类发出信息通知订阅者,发布者也被称为“事件源”;

(P187) 事件实质上是一种特殊的委托,通过多点委托的方法被多个方法订阅;

(P189)

匿名方法的方法体代码直接和委托对象关联,不需要指定委托对象名称;

实际编译时,匿名方法的名称由编译器自动分配;

(P192)

Lambda 表达式将 delegate 也隐藏了:(参数列表) => ;

.NET 的应用程序体系分为以下4个层次:程序集(Adembly)、模块(Module)、类型(Class)和类型成员(Member),反射技术可以在程序运行时获取这4个层次的元数据信息;

应用程序域是程序集层次上的更大的容器,一个应用程序域可以装载多个程序集;

(P201)

“Load()” —— 用于加载当前程序集位于相同目录下的外部程序集;

“LoadFrom()” —— 用于加载其它目录中的程序集;

(P203)

mscorlib 程序集包括了 .NET 大部分的基类库, CLR 运行时自动加载;

Assembly 类的 LoadFrom 方法需要传递外部程序集的完整路径;

(P204) 读取 AppDomain 类的 CurrentDomain 属性,可返回当前应用程序域,调用当前应用程序域的 GetAssemblies 方法,可获取所包含程序集的集合;

(P221) 进程包括多个应用程序域,而应用程序域可以加载多个程序集;

(P225)

如果需要异步调用委托对象所指向的方法,必须显式地调用 BeginiInvoke()方法,如果需要返回值则调用 EndInvoke()方法;

BeginInvoke()方法返回一个 IsAsyncResult 类型的对象而调用 EndInvoke()方法需要这个IAsyncResult 类型对象作为参数;

(P231) 默认情况下,手动创建的线程都是前台线程,而线程池中的线程只能是后台线程。只有前台线程全部结束,应用程序域才能被卸载(程序才能关闭)。前台线程全部结束后,后台线程即使没有完成工作,也会被忽略,并自动结束;

(P236)

lock(this) {需要同步的代码块;}

Monitor.Enter(this)

try

finally {Monitor.Exit(this);}

(P248)

自定义一个类类型,当该类型被标记了[Serializable]特性后,其对象即可被序列化;

(P249) XmlSerializer 类的构造函数需要传递参数,当只需要实现一个独立对象时,传递该对象所属类的 Type 对象类型即可,当该对象依赖于其它对象时,需要将其它对象所属类的 Type 对象类型作为数组传递;

(P264) this.控件对象.事件名称 + new EventHandler(事件处理方法名称);

(P268)

Application.Exit() 是退出整个应用程序;

this.Close() 是关闭指定的当前窗体;

(P268)

GDI+ 绘制功能的核心是 System.Drawing.Graphics 类,可以通过作为绘图区域窗体的 Paint 事件处理方法获取 Graphics 类对象,访问该方法所接接收的第2个参数的 Graphics 属性即可;

(P273)

SqlConnection 连接字符串 —— Server = 服务器名称; Database = 数据库名称; User ID = 用户名; Password = 密码;

OleDbConnection 连接字符串 —— Provider = SQLOLEDB; Data Source = 服务器名称; Initial Catalog = 数据库名称; User ID = 用户名; Password = 密码;

OdbcConnection 连接字符串 —— Driver = {SQL Server}; Server = 服务器名称; Database = 数据库名称; (或者) DSN = DSN 名称;

OracleConnection 连接字符串 —— Data Source = Oracle 8i; UserID = 用户名; Pwd = 密码;

(P274) 池化机制对“名称/值”对间的空格十分敏感;

(P283) 如果没有数据可操作,那么只能使用调用命令对象的 ExecuteReader 方法,返回一个数据读取器(DataReader 对象)。因为ExecuteNonQuery()与 ExecuteScalar()在没有数据调用时,就会出现“对象没有实例化”的错误,所以在判断是否有数据时,应该调用数据读取器的 Read()方法来检验;

(P284) DataReader 对象只能配合命令对象使用,而且 DataReader 对象在操作时连接对象营保持打开状态;

(P285) 数据读取器的 Read()方法可以检测是否还有下一条数据,有则返回true,没有则返回 false 。相应地, NextResult()方法可以检测是否还有下一个表的结果集,有则返回 true ,并且数据读取器将返回下一个结果集的数据,没有则返回 false;

(P293) DataReader 只能向前读取数据,每次读取一条记录(内存中瞬间只保存一条记录),读取完成后不能进行任何数据操作;

(P296) 由于 CommandBuilder 会使程序性能下降,因此应该避免大数据量批量更新,为了提高性能,应该使用存储过程;

(P310) 当字段名、表名和数据库名作为变量时,只能采用动态 SQL 语句方式,使用 exec() 或者 exec sp_exexutesql 执行;

(P317) UPDATE 事务先执行一个 DELETE 操作,再执行一个 INSERT 操作,执行过的行首先被转移到 deleted 表,让新行同时添加到激活触发器的表中和 inserted 表中;

(P319) 指定 GROUP BY 时, GROUP BY 表达式必须与选择列表的表达式严格匹配,即选择列表中任何非聚合表达式的每个字段名(列)必须包含在 GROUP BY 列表中;

(P335) 在 TCP/IP 协议中,HTTP 协议即(超文本传输协议)位于 TCP/IP 协议的应用层,主要用于传输网页文件;

(P338) AutoEventWireup 属性设置为 true 时,服务器端的事件将自动绑定。如果开发者需要某个事件的处理方法使用自定义名称,则只需设置 AutoEventWireuo 属性为 false ;

(P344) 页面类的 Server 属性可返回 System.Web.HttpServer.Utility 类的对象。简称其为 Server 对象(严格说应该是 Http Server Utility 对象)。

(P349)

“Web 服务器控件” —— 该控件运行于服务器端,根据代码执行结果生成一个或者多个 HTML 控件,而不是直接描述 HTML 控件;

Web服务器控件的事件处理在服务器端,并且状态可以保存到 ViewState (试图状态)中。

(P350) 用户控件实现了完全的类化,并最大程度封装了代码块,使代码维护更加方便,也提高了数据的安全性;

(P359)

FileUpload 控件的 PostedFile 属性可返回 HttpPostedFile 对象;

ASP.NET 的 Web 应用程序默认将上传文件限制于 4MB 以下, 如果需要修改这个限制,可以在 Web.Config 配置文件中修改 HttpRuntime 配置元素的 MaxRequestLength 属性值(单位为千字节)即可。当用户上传的文件大小超过了该属性值,上传将失败,并且页面内容为“此程序无法显示网页”的页面;

(P360) form 元素会自动提交到自身页面上。如果没有指定 method 属性,它会默认地设置为 “Post”。如果用户没有指定 name 和 id 属性,ASP.NET 会自动地给予分配;

(P361) 每个控件的 ID 属性被保存到 ViewState 中;

(P362) 在 *.aspx 页面中,如果 form 元素的 runat 属性值为“server”,则该页面所生成的 HTML 页面具备了 ViewState 功能;

(P364) ViewState 只在页面内有效,不能跨页面使用;

(P372) 使用非进程内方法存储 Session 值应确保 HttpSessionState 对象内的自定义类型是可序列化的,即类型被标记了[Serializable]特性;

(P382) mode 属性值为“On” 时代表始终显示自定义(友好的)信息,如果没有设置 DefaultRedirect 属性,用户将看到一般的错误信息,而 mode 属性值为“Remote Only”时代表只对不在本地 Web 服务器上运行的用户显示自定义(友好的)信息;

(P385) ASP.NET 应用程序下每个子目录都可以有继承于根目录配置文件的 Web.Config 文件, 但一个应用程序只能有一个身份验证登录页面。即以上代码中 <forms> 子节点 loginUrl 属性所指的页面。如果在子目录的 Web.Config 文件中出现了 <authentication> 节点的配置,程序将出错,除非将此目录配置为虚拟目录进行访问;

(P390)

<% %> 是服务器端的输出指令,包含输出到页面的程序代码;

<%# %> 是数据绑定表达式语法;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值