C#基础知识复习题
1、new有几种用法?
答:1、new Class();
2、覆盖方法,public new XXXX();
3、new 约束指定泛型类声明中的任何类型参数都必须有公共的无参数构造函数
2、用sealed修饰的类有什么特点?
答:sealed修饰符用于防止从所修饰的类派生出其他类。如果一个密封类指定为其他类的基类,则会发生编译错误。
密封类不能同时为抽象类。
sealed修饰符主要用于防止非有意的派生,他还能促使某些运行时优化。
String就是用sealed修饰的密封类,所以不能被继承。
3、在.NET中,配件的意思是?
答:程序集。(中间IL语言、元数据、资源、装配清单)
4、一个数组:1,1,2,3,5,8,13,21...,求第30位数是多少?
答:int[] arr = new int[30];
arr[0] = 1;
arr[1] = 1;
for (int i = 2; i < arr.Length; i++)
{
arr[i] = arr[i-1] + arr[i-2];
}
Console.WriteLine(arr[29]);
Console.ReadLine();
5、请简述面向对象的多态的特性及意义
答:简单来说,多态是具有表现多种形态的能力特征,在OO中是指,语言根据对象的类型的不同,以不同的方式处理。
特别是重载方法和继承类这种形式的能力。
多态被认为是面向对象语言的必备特性。
面向对象的语言使用虚方法表达多态。
这意味着派生类可以有和父类具有同样签名的方法,并且父类可以调用派生类的方法。
在C#中,必须使用virtual关键字才能使方法被父类调用。
6、请编程遍历winform窗口上所有TextBox控件,并给它的Text属性赋值为string.Empty。
答:using System.Windows.Forms;
foreach (Control control in this.Controls)
{
if(control is TextBox)
{
TextBox tb = (TextBox)control;
tb.Text = String.Empty;
}
}
7、什么是装箱(inboxing)和拆箱(unboxing)。
答:装箱:将一个值类型隐式地转换成一个object类型,或把这个值类型转换成一个被该值类型应用的接口类型,把一个值类型的值装箱,就是创建一个object实例并将值复制给这个object
拆箱:和装箱相反,拆箱转换是指将一个对象类型显式地转换成一个值类型,或将一个接口类型显式地转换成一个执行该接口的值类型。
object obj = null;
obj = 1;//装箱,把值类型包装成引用类型。
int num = (int)obj;// 拆箱,显示类型转换。
8、如何理解三层架构。
答:三层架构就是将整个业务应用划为:表现层、业务逻辑层、数据访问层。
区分层次的目的即为了“高内聚,低耦合”的思想。
表现层:通俗讲就是展现给用户的界面,即用户在使用一个系统的时候的所见所得。
业务逻辑层:针对具体问题的操作,也可以说是对数据层的操作,对数据业务逻辑处理。
数据访问层:该层所做事务直接操作数据库,针对数据的增删改查等。
每层之间是一种垂直关系。
三层架构是N层架构的一种,一般来说,层次之间是向下依赖的,下层代码未确定其接口前,上层代码是无法开发的,下层代码接口的变化将使上层的代码一起变化。
优点:分工明确,条理清晰,易于调试,而且具有扩展性。
缺点:增加系统复杂度,增加成本。
9、写一个冒泡排序(从小到大)。
答:using System.Windows.Forms;
foreach (Control control in this.Controls)
{
if(control is TextBox)
{
TextBox tb = (TextBox)control;
tb.Text = String.Empty;
}
}
10、数据库三范式是什么?
答:1NF,确保每列保持原子性
2NF,确保表中的每列都和主键相关
3NF,确保每列都和主键列直接相关,而不是间接相关
11、能用foreach遍历访问的对象有什么要求?
答:需要实现IEnumerable接口或声明GetEnumerator方法的类型。
12、GC是什么?为什么要有GC?
答:GC是垃圾收集器。
程序员不用担心内存管理,因为垃圾收集器会自动进行管理。
GC只能处理托管内存资源的释放,对于非托管资源则不能使用GC回收内存,必须由程序员手工回收。
13、说出五个集合类。
答:List、Dictionary、Stack、Queue、Tree等
14、不用JQuery等库,原生JS使用AJAX实现登陆。
答:window.onload = function () {
document.getElementById('btn').onclick = function () {
var username = document.getElementById('username').value;
var password = document.getElementById('password').value;
var xhr = new XMLHttpRequest();
xhr.open('POST','/url?username=' + username + '&password=' + password, true);
xhr.onreadystatechange = function () {
if(xhr.readyState === 4) {
if (xhr.status === 200) {
alert('登陆成功')
} else {
alert('登陆失败')
}
}
}
}
}
15、你觉得如何才能提高代码的效率和性能(可以列举多种思路,越多越好)?
答:可以根据业务流程、业务数据的特点进行优化,比如可以采用缓存、索引等来提高代码的效率和性能。
同时不要进行无意义的代码优化,重点优化系统的性能瓶颈。
按照设计模式去编写代码,彻底的面向对象编程,多用委托事件。
尽量做到方法的每一个实现代码只写一遍。
16、什么是Code-Behind技术?
答:Code-Behind是代码隐藏。
在ASP.NET中通过ASPX页面指向CS文件的方法显示逻辑和处理逻辑的分离,这样有助于web应用程序的创建。
Code-Behind是基于部分类技术实现的。
17、using关键字有什么用?什么是IDisposable?
答:using可以声明namespace的引入,还可以实现非托管资源的释放,实现了IDisposable的类在using中创建对象,using结束后会自动调用Dispose方法,释放资源。
using其实等价于于try...finally,用起来更方便。
18、String是值类型还是引用类型?它是如何工作的。
答:String是引用类型。
String的值是不可变的,当对String类型的对象重新赋值时,这个对象的引用指向就会变成一个新的引用,而原来的那个值并没有改变,只是引用改变了。
19、简述堆与栈的区别。
答:栈是编译期间就分配好的内存空间,因此你的代码中必须就栈的大小有明确的定义;
局部值类型变量、值类型参数等都在栈中。
堆是程序运行期间动态分配的内存空间,你可以根据程序的运行情况确定要分配的堆内存的大小。
20、有一个8个数的数组{1,2,3,3,4,5,6,6},计算其中不重复数字的个数。
答:int values = {1,2,3,3,4,5,6,6};
HashSet<int> set = new HashSet<int>();
foreach(int i in values)
{
set.Add(i);
}
Console.WriteLine(set.Count)
21、是否可以从一个static方法内部发出对非static方法的调用?
答:不可以。因为非static方法与对象相关联,必须创建一个对象后,才可以在该对象上进行方法调用,而static方法调用时不需要创建对象,可以直接调用。
也就是说,当一个static方法被调用时,可能还没有创建任何实例对象,如果从一个static方法中调用一个static方法,那么非static方法没有关联的对象,所以不可以。
22、说出一些常用类、接口,请各列举5个。
答:类:StreamReader、StringBuilder、SqlConnection、FileStream、File、Regex
接口:IDisposable、IEnumerable、IComparable、ICollection、IList
23、C#支持多重继承么?
答:类之间不支持,接口之间支持。
类对接口叫做实现,不叫继承。
类是爹、接口是能力,能力可以有多个,但不能有多个爹。
24、简单说明数据库建立索引的优缺点。
答:优点,使用索引可以加快数据的查询速度。
缺点,插入数据过程中会建立索引,所以会降低数据的插入、更新速度,还会占用磁盘。
如果一个表查询比写入频繁可以建立索引,如果写入比查询频繁,就不建议建立索引。
25、SQL注入漏洞产生的原因?如何防止。
答:程序开发过程中不注意书写sql语句和对特殊字符进行过滤,导致客户端可以提交一些sql语句正常执行。
(1)sql语句尽量不要省略引号和单引号。
(2)过滤掉SQL语句中的一些关键字。
(3)控制错误信息,不要再浏览器上输出错误信息。
(4)使用SqlParameter类,尽量不要拼接字符串SQL语句。
26、如何提高页面的显示速度?假如一个页面的加载时间是10.89S,你会用什么样的方式优化。
答:首先要找出问题所在,是服务器端运行的速度慢还是服务器端到客户端的下载慢还是页面在浏览器的加载速度慢。
如果是服务器端运行速度慢,则找是数据库的原因还是算法的问题,如果是数据库的问题则尝试添加索引、优化SQL语句,如果是算法的问题,则优化算法。
如果对于一些不经常改动的页面可以使用静态页技术!
对于一些数据不需要及时更新的而且取数据的过程非常耗时可以使用缓存。
页面中的内容可以按需加载(比如说可以像网站的评论那样当用户需要看的时候再加载其内容)
可以在图片需要显示的时候再进行加载。
如果是服务器端到客户端的下载慢则看是页面体积过于臃肿还是网络问题,
如果是页面体积过于臃肿,则优化HTML代码,去掉无用的标签,压缩JS、CSS,可以用CSS Spirit技术将多个图片放到一个图片中,减少向服务器的请求。
如果是网络问题,则尝试在不同的网络、地区部署服务器,然后使用CDN技术加速访问。
如果是页面中的JavaScript运行复杂导致运行速度慢,则优化JavaScript。
27、你会采用什么样的策略和方法来实现系统缓存。
答:在ASP.NET中 缓存有 页面缓存,数据源缓存,和一些自己定义的缓存!
对于那些整个页面不经常变化的我们可以使用页面缓存,而对于那些执行非常耗时的SQL语句并且数据的及时性要求不高的我们可以使用数据源缓存。
28、网站想要实现文件防盗链的功能,说说你的解决方案。
答:读取HTTP报文头中的UrlReferrer在Application_BeginRequest中我们可以判断用户的请求是否来源于本网站。如果不是我们可以终止用户的请求。
29、StringBuilder和String的区别。
答:String 在进行运算时(如赋值、拼接等)会产生一个新的实例,而 StringBuilder 则不会。
所以在大量字符串拼接或频繁对某一字符串进行操作时最好使用 StringBuilder,不要使用 String
如果要操作一个不断增长的字符串,尽量不用String类,改用StringBuilder类。
两个类的工作原理不同:String类是一种传统的修改字符串的方式,它确实可以完成把一个字符串添加到另一个字符串上的工作没错,但是在.NET框架下,这个操作实在是划不来。
因为系统先是把两个字符串写入内存,接着删除原来的String对象,然后创建一个String对象,并读取内存中的数据赋给该对象。这一来二去的,耗了不少时间。
而使用System.Text命名空间下面的StringBuilder类就不是这样了,它提供的Append方法,能够在已有对象的原地进行字符串的修改,简单而且直接。
当然,一般情况下觉察不到这二者效率的差异,但如果你要对某个字符串进行大量的添加操作,那么StringBuilder类所耗费的时间和String类简直不是一个数量级的。
30、对于大流量的网站,应采用什么样的方法来解决访问量问题。
答:首先,确认服务器硬件是否足够支持当前的流量。
普通的P4服务器一般最多能支持每天10万独立IP,如果访问量比这个还要大,那么必须首先配置一台更高性能的专用服务器才能解决问题,否则怎么优化都不可能彻底解决性能问题。
其次,优化数据库访问。
服务器的负载过大,一个重要的原因是CPU负荷过大,降低服务器CPU的负荷,才能够有效打破瓶颈。而使用静态页面可以使得CPU的负荷最小化。
前台实现完全的静态化当然最好,可以完全不用访问数据库,不过对于频繁更新的网站,静态化往往不能满足某些功能。
缓存技术就是另一个解决方案,就是将动态数据存储到缓存文件中,动态网页直接调用这些文件,而不必再访问数据库,WordPress和Z-Blog都大量使用这种缓存技术。
如果确实无法避免对数据库的访问,那么可以尝试优化数据库的查询SQL.避免使用Select * from这样的语句,每次查询只返回自己需要的结果,避免短时间内的大量SQL查询。
第三,禁止外部的盗链。
外部网站的图片或者文件盗链往往会带来大量的负载压力,因此应该严格限制外部对于自身的图片或者文件盗链。
第四,控制大文件的下载。
大文件的下载会占用很大的流量,并且对于非SCSI硬盘来说,大量文件下载会消耗CPU,使得网站响应能力下降。因此,尽量不要提供超过2M的大文件下载, 如果需要提供,建议将大文件放在另外一台服务器上。
第五,使用不同主机分流主要流量
将文件放在不同的主机上,提供不同的镜像供用户下载。
第六,使用流量分析统计软件
在 网站上安装一个流量分析统计软件,可以即时知道哪些地方耗费了大量流量,哪些页面需要再进行优化,因此,解决流量问题还需要进行精确的统计分析才可以。