ASP.NET vs MVC vs WebForms

 

许多ASP.NET开发人员开始接触MVC认为MVC与ASP.NET完全没有关系,是一个全新的Web开发,事实上ASP.NET是创建WEB应用的框架而MVC是能够用更好的方法来组织并管理代码的一种更高级架构体系,所以可以称之为ASP.NET MVC。

我们可将原来的ASP.NET称为 ASP.NET Webforms,新的MVC 称为ASP.NET MVC.

ASP.NET Web Form

ASP.NET 在过去的十二年里,已经服务并成功实现Web 应用的开发。我们首先了解一下为什么ASP.NET能够如此流行,并成功应用。

微软编程语言从VB开始就能够成为流行并广泛应用,都源于其提供的强大的Visual studio能够进行可视化的编程,实现快速开发。

使用VS时,开发人员能够通过拖拽UI元素,并在后台自动生成这些界面的代码。称为后台代码。在后台代码中开发人员可以添加操作这些UI元素的逻辑代码。

clip_image002

因此微软的可视化RAD架构体系有两方面组成,一方面是UI,一方面是后台代码。因此ASP.NET Web 窗体,包含ASPX和ASPX.CS,WPF包含XAML/XAML.CS等。

ASP.NET Web Form存在的问题

我们不得不考虑的问题是,既然ASP.NET Web Form 如此成功且具有优势,为什么微软还要推出ASP.NET MVC?主要是因为ASP.NET Webform的性能问题。在Web应用程序中从两方面来定义性能:

1. 响应时间: 服务器响应请求的耗时

2. 带宽消耗: 同时可传输多少数据。

响应时间

我们可以理解为什么ASP.NET Webform比较慢,如图我们做了一些小的加载测试。分别使用ASP.Net MVC和ASP.Net Webform,发现ASP.Net MVC的响应时间比Webform快了两倍。

clip_image003

接下来我们在思考一个问题为什么ASP.NET MVC的性能更好?看看下面这个示例,简单的UI代码和UI的后台代码。

假如一个textbox的ASPX页面:

<asp:TextBox ID="TextBox1" runat="server">

对应的UI后台代码:

   1:  protected void Page_Load(object sender, EventArgs e)
   2:  {      
   3:        TextBox1.Text = "Make it simple";            
   4:        TextBox1.BackColor = Color.Aqua;
   5:  }

运行结果:

clip_image004

如果查看HTML输出,则会显示如下代码:

<input name="TextBox1" type="text" value="Make it simple" id="TextBox1" style="" />

我们再来思考上面提到的问题

1. 这种HTML生成方式是否很有效?我们是否为了获取如此简单的HTML而长时间的消耗服务器

2. 开发人员是否可以直接编写HTML?很难实现吗?

 

clip_image005

通过分析我们可以得知,每一次请求都有转换逻辑,运行并转换服务器控件为HTML输出。如果我们的页面使用表格,树形控件等复杂控件,转换就会变得很糟糕且非常复杂。HTML输出也是非常复杂的。由于这些不必要的转换从而增加了响应时间。该问题的解决方案就是摆脱后台代码,写成纯HTML代码。

带宽消耗

ASP.NET开发人员都非常熟悉Viewstates,因为它能够自动保存post返回的状态,减少开发时间。但是这种开发时间的减少会带来巨大的消耗,Viewstate增加了页面的大小。在做的加载测试中,与MVC 对比,我们发现Viewstate增加了两倍的页面存储。以下是测试结果:

 

clip_image006

页面尺寸的增加是因为viewstate产生了额外的字节。下图就是Viewstate的截图。许多人可能会不同意此观点,但是众所周知,开发人员是如何工作的,如果有选择,他们肯定会采取别的选择。

 

clip_image008

  1. HTML 消耗

现在因为我们都是后台代码和ASP.NET web server控件的努力,我们对于怎样得到HTML以及如何使他们更有效没有更好的办法。如下面展示的ASPX 代码,你能确定会生成什么样的HTML代码吗?


  • <asp:Label ID="Label1" runat="server" Text="I am label">

     
  •   
    <asp:Literal ID="Literal1" runat="server" Text="I am a literal">
     
  • <asp:Panel ID="Panel1" runat="server">I am a panel

     

     

Lable标签会生成DIV标签还是SPAN标签?运行后生成的HTML代码的结果如下:label生成了span标签,Literal生成了转换为了简单的文本,而panel转换为了DIV标签。

 <span id="Label1">I am label</span>I am a literal

  • I am a panel

因此与其生成HTML代码,还不如直接编写HTML代码,并实现HTML控件。

所以该问题的解决方案是:不使用服务器控件,直接编写HTML代码。

直接编写HTML代码的好处在于web设计者可以与开发人员紧密合作及时沟通。设计人员可以使用他们喜爱的设计工具来设计HTMl代码,像dream weaver,前端页面等,设计独立。如果我们使用服务器控件,这些设计者工具可能不会识别。

       2. 后台代码类的重用性
如果仔细观察一些专业的ASP.NET Webform项目,你会发现后台代码类往往都包含了大量的代码,并且这些代码也是非常复杂的。而现在,后台代码类继承了“System.Web.UI.Page”类。但是这些类并不像普通的类一样能够到处复用和实例化。换句话来讲,在Weform类中永远都不可能执行以下代码中的操作:
   1: WebForm1 obj = new WebForm1();obj.Button1_Click();

 

  •   3. 单元测试

既然无法实例化后台代码类,单元测试也是非常困难的,也无法执行自动化测试。必须手动测试。

  • 解决方案

既然讲了ASP.Net Webform存在的两大问题即服务器控件和后台代码,以下是根源图,

clip_image009

那么解决方案是什么?

就是我们需要将后台代码迁移到独立的简单的类库,并且拜托ASP.Net服务器控件,并写一些HTML示例。

ASP.NET Webform 和MVC 比较,如下图:

clip_image010

Microsoft Asp.Net MVC 是如何弥补Web Form存在的问题的?

后台代码和服务器控件是一切问题的根源。所以如果你查看当前的WebForm体系结构,开发者正在使用的包含3层体系结构。三层体系结构是由UI包含ASPX及CS 后台代码。

UI,业务逻辑以及包含数据访问的中间层

clip_image011

Asp.Net MVC 由Model,View,Controller三部分组成。Controller中包含后台代码逻辑,View是ASPX,如纯HTML代码,Model是中间层。通过上图可获得这三部分的关系。

所以会发现MVC的改变有两点,View变成简单的HTML,后台代码移到简单的.NET类中,称为控制器。

以下是ASP.NET MVC 请求流的通用步骤:

Step 1:首先获取控制器。

Step 2:依赖行为控制器创建Model对象,Model通过转换调用数据访问层。

Step 3:数据填充Model之后,传递到View 显示层,实现显示的目的。

clip_image012

到这里我们就已经了解了ASP.Net MVC的各个组件。下面我们做一些小的实验深入了解MVC的各组件。首先我们从Controller 控制器开始,因为Controller是MVC体系架构的核心部分。

你是否真的理解Asp.Net MVC的Controller(控制器)?

为了我们能够更好的理解Controller,我们首先需要理解Controller中涉及的专业术语:用户交互逻辑。

什么是用户交互逻辑?

场景1

你是否想过当用户输入URL摁下回车键时,会发生什么事情?

clip_image013

浏览器首先需要给服务器发送请求,服务器再做出响应。

clip_image014

通过这些请求之后,客户端正尝试与服务器交互,服务器能够反馈响应,因为服务器端存在一些判断逻辑来处理这些请求。这些能够处理用户请求以及用户交互行为的业务逻辑称为用户交互逻辑。

场景2

有一种常见的情况,服务器端发送的请求是HTML请求。HTML请求是由一组输入控件和提交按钮组成的。

clip_image015

当用户点击“Save”按钮之后会发生什么?

如果你的回答是有一些事件处理器来处理button点击事件,那么很抱歉回答是错误的。

在Web编程中是没有事件的概念的,Asp.net Web forms 根据我们的行为自动添加了处理代码,所以给我们带来的错觉认为是事件驱动的编程。这只是一种抽象的描述。

当点击Button时,一个简单的HTTP请求会发送到服务器。差别在于Customer Name,Address以及Age中输入的内容将随着请求一起发送。最终,如果是有个请求,服务器端则有对应的逻辑,使服务器能够更好响应请求。简单来说是将用户交互逻辑写在服务器端。

在Asp.Net MVC中,C代表Controller,就是用来处理用户交互逻辑的。

实验一:简单的MVC Hello world,着重处理Controller。

  • Step1 创建一个Asp.Net MVC 5项目

打开Visual studio 2013 点“文件”->新建->项目。

clip_image016

  • Step 1.2 选择Web 应用,输入项目名称,选择存放路径,点击确定。

clip_image017

  • Step 1.3 选择MVC 模板

clip_image018

  • Step 1.4 选择Change Authentication(改变授权),弹出对话框中选择“No Authentication”,并点击确定。

clip_image019

  • Step 2 –创建控制器
  • Step 2.1,在资源管理器中,右击controller文件夹,选择添加->Controller(控制器)

clip_image020

  • Step 2.2 选择空 MVC 5 Controller 并点击添加

clip_image021

  • Step 2.3 输入控制器的名称”TestController“,点击添加。

在这一步骤中,要特别注意千万不能删除名称中的” Controller”关键字。名称中必须包含Controller关键字。

clip_image022

  • Step 3. 创建行为方法

打开新建的TestController 类,可以发现已生成的Index 方法,将该方法删除,并且添加新方法命名为GetString ,代码如下:

   1:  public class TestController : Controller
   2:  {
   3:      public string GetString() 
   4:     {        return "Hello World is old now. It’s time for wassup bro ;)"; 
   5:   
   6:    }
   7:  }
  • Step 4. 运行并测试 按 F5 键,在地址栏中以“ControllerName/ActionName”这样的形式输入,需要注意的输入控制器名称时,不能输入”Controller“只输入”Test”。

clip_image023

 

实验一:Q&A

1. TestController 和Test之间的关系是什么?

TestController是类名称,而Test是Controller的名称,请注意,当你在URL中输入controller的名称,不需要输入Controller这个单词。

2. Action(行为) 方法是什么?

Action 方法 简单的来说就是一个Controller内置的public类型的方法,能够接收并处理用户的请求,上例中,GetString 方法返回了一个字符串类型的响应。

注意:在Asp.Net Web Forms中默认的返回请求是HTML的,如果需要返回其他类型的请求,就必须创建HTTP 处理器,重写内容类型。这些操作在Asp.net中是很困难的。在Asp.net MVC中是非常简单的。如果返回类型是”String“直接返回,不需要发送完整的HTML。

3. 如果从Action 方法中返回对象值会出现什么意外情况?

请浏览以下代码

   1:  namespace WebApplication1.Controllers
   2:  {
   3:      public class Customer
   4:      {
   5:          public string CustomerName { get; set; }
   6:          public string Address { get; set; }
   7:      }
   8:      public class TestController : Controller
   9:      {
  10:          public Customer GetCustomer()
  11:          {
  12:              Customer c = new Customer();
  13:              c.CustomerName = "Customer 1";
  14:              c.Address = "Address1";
  15:              return c;
  16:          }
  17:      }
  18:  }

 输出结果如下所示: 

 

 

当返回类型如“Customer”这样类似的对象时,将调用ToString()方法,返回“NameSpace.ClassName”形式的类名。

4. 如果需要获得上面例子中的属性值,要如何操作?

简单重写类的“ToString”方法,如下:

   1:  public override string ToString()
   2:  {
   3:       return this.CustomerName+"|"+this.Address;
   4:  }

 

 

运行结果:

clip_image025

5. Action 方法是否只能用Public修饰符来修饰?

答案是肯定的,每个公有方法都会自动称为Action 方法。

6. 非public方法是什么?

类的方法都比较简单,并且并不是公共可用的。无法在Web中调用。

7. 如果我们需要其他函数来完成一些特定功能,但不是Action Method要如何实现?

使用NonAction属性修饰,如下:

 

 

   1:  [NonAction] 
   2:  public string SimpleMethod()
   3:  { 
   4:     return "Hi, I am not action method";
   5:  }

 

 

当尝试给以上Action 方法发送请求时,会获得以下结果: 

clip_image026

View部分

Controller是处理用户请求,并做出响应,通常情况下响应都是以显示在浏览器中,使用HTML代码,浏览器才可识别。HTML有图像,文本,输入控件等。通常称为用户界面的设计即UI层,在ASP.net MVC称为View。

实验二——深入理解View

在实验二中,创建一个简单的MVC应用,仅仅具有Controller和简单的字符串类型的返回值。让我们来了解MVC中的View部分吧。

  • Step1 –创建新的Action 方法

在TestController中添加新的Action 方法,如下:

   1:  public ActionResult GetView()
   2:  { 
   3:     return View("MyView");
   4:  }

 

  • Step 2 创建View
  • Step 2.1 右击上述创建的Action 方法,选择“添加View”

 

clip_image027

  • Step 2.2 在添加View的对话框中输入View名称“MyView”,取消选择“使用布局”的复选框,点击添加。

clip_image028

资源管理器重的Views/Test文件夹中会添加一个新的View文件。

clip_image029

  • Step3 在View中添加内容

打开MyView.cshtml 文件,并添加以下内容:

@{Layout = null;}
<!DOCTYPE html>
<html><head><meta name="viewport" content="width=device-width" /> <title>MyView</title> </head><body>Welcome to MVC 5 Step by Step learning
</body></html>
  • Step 4. 运行 按F5键运行应用

clip_image030

实验二:Q&A

1. 为什么View会放在Test的文件夹中?

View是与放置在特定目录下的Controller相关。这个特定文件夹是以”ControllerName”命名的,并且放在View文件夹内

2. 在多个控制器中无法重用View吗?

当然可以,我们需要在将这些文件放在特定的Shared文件夹中。将View 放在Shared文件夹中所有的Controller都可用。

clip_image031

3. 单个Action 方法中可引用多个View吗?

可以,ASP.NET MVC的view和Controller不是严格的匹配的,一个Action Method可以引用多个view,而一个View也可以被一个Action方法使用如下代码所示:

   1:  public ActionResult GetView()
   2:  {
   3:      if(Some_Condition_Is_Matching)
   4:      { 
   5:         return View("MyView");
   6:      }
   7:      else
   8:      {
   9:         return View("YourView");
  10:      }
  11:  }

 

 

4. View函数的功能是什么?

 创建 ViewResult 对象将会渲染成视图来给用户反馈

 

  • ViewResult 创建了ViewPageActivator 对象
  • ViewResult 选择了正确的ViewEngine,并且会给ViewEngine的构造函数传ViewPageActivator对象的参数
  • ViewEngine 创建View类的对象
  • ViewEngine 调用View的RenderView 方法。

5. ActionResult和 ViewResult的关系是什么?

ActionResult是抽象类,而ViewResult是ActionResult的多级孩子节点,多级是因为ViewResult是ViewResultBase的子类,而ViewResultBase是ActionResult的孩子节点。

6. 什么是ContentResult?

ViewResult是HTML响应而ContentResult是标准的文本响应,仅返回字符串类型。区别就在于ContentResult是ActionResult的子类。

 

要进行ASP.ET MVC的开发,不但需要具备MVC的知识,还需要高效的工具来帮助开发。

使用 ComponentOne Studio Enterprise 中提供的 ComponentOne Studio ASP.NET MVC 版本,您能获取快速的轻量级控件来满足用户所有需求。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/284409.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

在Blazor 中自定义权限验证

Blazor是什么Blazor 是微软在 .NET 里推出的一个 WEB 客户端 UI 交互的框架&#xff0c;使用 Blazor 你可以代替 JavaScript 来实现自己的页面交互逻辑&#xff0c;可以很大程度上进行 C# 代码的复用&#xff0c;Blazor 对于 .NET 开发人员来说是一个不错的选择。需求背景其实我…

【ArcGIS微课1000例】0035:地图面状符号设计教程

地图符号是表示地图内容的基本手段,它由形状不同、大小不一、色彩有别的图形和文字组成。 地图符号是地图的语言,是一种图形语言。它与文字语言相比较,最大的特点是形象直观,一目了然。 本文讲解ArcGIS中面状符号设计方法。 文章目录 一、新建符号样式二、面状符号设计1. 斜…

MySQL夺命15问,你能坚持到第几问?

前言 MySQL在面试中经常被问到&#xff0c;本文总结了面试中的经典问题。 1. 数据库三大范式是什么&#xff1f; 第一范式&#xff1a;每个列都不可以再拆分。 第二范式&#xff1a;在第一范式的基础上&#xff0c;非主键列完全依赖于主键&#xff0c;而不能是依赖于主键的一部…

ios元素定位

原文地址http://www.cnblogs.com/meitian/p/7373460.html 第一种&#xff1a;通过Appium1.6的Inspector来查看 具体安装方式前面的随笔已经介绍了&#xff1a;http://www.cnblogs.com/meitian/p/7360017.html可以通过定位找到元素xpath或name个人不推荐用这个方法&#xff0c;实…

使用 LSM-Tree 思想基于.NET 6.0 C# 写个 KV 数据库(案例版)

文章有点长&#xff0c;耐心看完应该可以懂实际原理到底是啥子。这是一个KV数据库的C#实现&#xff0c;目前用.NET 6.0实现的&#xff0c;目前算是属于雏形&#xff0c;骨架都已经完备&#xff0c;毕竟刚完工不到一星期。当然&#xff0c;这个其实也算是NoSQL的雏形&#xff0c…

35.使用拦截器实现权限验证

转自&#xff1a;https://wenku.baidu.com/view/84fa86ae360cba1aa911da02.html 为了说明此问题&#xff0c;我们建立struts2auth项目&#xff0c;流程图如下&#xff1a; 简短说明&#xff1a;当我们访问main.jsp页面&#xff0c;并试图通过此页面中的链接地址&#xff1a;not…

如何保证缓存和数据库的一致性?

1. 问题分析 2. Cache-Aside 2.1 读缓存 2.2 写缓存 2.3 延迟双删 2.4 如何确保原子性 3. Read-Through/Write-Through 3.1 Read-Through 3.2 Write-Through 4. Write Behind 很多小伙伴在面试的时候&#xff0c;应该都遇到过类似的问题&#xff0c;如何确保缓存和数据库…

Pressed状态和clickable,duplicateParentState的关系

做Android开发的人都用过Selector,可以方便的实现View在不同状态下的背景。不过&#xff0c;相信大部分开发者遇到过和我一样的问题&#xff0c;本文会从源码角度&#xff0c;解释这些问题。 首先&#xff0c;这里简单描述一下&#xff0c;我遇到的问题&#xff1a; 界面上有个…

【招聘(南京)】 慧咨环球南京研发中心 .NET和Blazor 前端

主要的亮点快速增长的、产品导向型的全球性科技公司设计和开发市场领先的软件解决方案WLB — 工作生活相平衡澳洲排名前五的软件公司混合办公 — 3天在家办公&#xff0c;2天在办公室办公在C#和.NET开发&#xff0c;企业级系统研发&#xff0c;软件工程方面有长期的优秀实践和技…

用Python+Django在Eclipse环境下开发web网站【转】

一、创建一个项目如果这是你第一次使用Django&#xff0c;那么你必须进行一些初始设置。也就是通过自动生成代码来建立一个Django项目--一个Django项目的设置集&#xff0c;包含了数据库配置、Django详细选项设置和应用 特性配置&#xff0c;具体操作步骤如下所示。 1.新建Djan…

[转]数据结构KMP算法配图详解(超详细)

KMP算法配图详解 前言 KMP算法是我们数据结构串中最难也是最重要的算法。难是因为KMP算法的代码很优美简洁干练&#xff0c;但里面包含着非常深的思维。真正理解代码的人可以说对KMP算法的了解已经相当深入了。而且这个算法的不少东西的确不容易讲懂&#xff0c;很多正规的书本…

BGP-MED-2

BGP-MED-2如图&#xff1a;当AS100去往AS300的60、10的网络时&#xff0c;60走R3&#xff0c;10走R1!使用MED属性影响选路&#xff01; R2的配置 bgp 200peer 1.1.1.1 as-number 100 peer 1.1.1.1 ebgp-max-hop 255 peer 1.1.1.1 connect-interface LoopBack0peer 4.4.4.4 as-n…

WPF 实现 Gitee 气泡菜单(一)

WPF 实现 Gitee 气泡菜单&#xff08;一&#xff09;气泡菜单&#xff08;一&#xff09;作者&#xff1a;WPFDevelopersOrg原文链接&#xff1a; https://github.com/WPFDevelopersOrg/WPFDevelopers框架使用大于等于.NET40&#xff1b;Visual Studio 2022;项目使用 MIT 开…

[转]LVS负载均衡(LVS简介、三种工作模式、十种调度算法)

一、LVS简介 LVS&#xff08;Linux Virtual Server&#xff09;即Linux虚拟服务器&#xff0c;是由章文嵩博士主导的开源负载均衡项目&#xff0c;目前LVS已经被集成到Linux内核模块中。该项目在Linux内核中实现了基于IP的数据请求负载均衡调度方案&#xff0c;其体系结构如图1…

一张图看懂微软Power BI系列组件

一、Power BI简介 Power BI是微软最新的商业智能&#xff08;BI&#xff09;概念&#xff0c;它包含了一系列的组件和工具。话不多说&#xff0c;直接上图吧&#xff1a; Power BI的核心理念就是让我们用户不需要强大的技术背景&#xff0c;只需要掌握Excel这样简单的工具就能快…

互联网项目总结

2019独角兽企业重金招聘Python工程师标准>>> 从去年年底开始专门被分配到互联网小组做项目&#xff0c;一直想做个总结&#xff0c;但是苦于太贪玩。好吧&#xff0c;借着小组技术交流来一发。这里只对自己新学习的技术或者一些小技巧做简要概述&#xff0c;不做深究…

【ArcGIS微课1000例】0036:分式标注案例教程

【拓展阅读】:【ArcGIS Pro微课1000例】0015:ArcGIS Pro中属性字段分式标注案例教程 文章目录 1. 符号化2. 分式标注1. 符号化 右键数据图层→符号系统,打开符号系统对话框,住符号系统选择【唯一值】,字段1选择NAME。 唯一值标注效果: 2. 分式标注 双击打开图层属性,切…

【转】 ConstraintLayout 完全解析 快来优化你的布局吧

转自&#xff1a; http://blog.csdn.net/lmj623565791/article/details/78011599 本文出自张鸿洋的博客 一、概述 ConstraintLayout出现有一段时间了&#xff0c;不过一直没有特别去关注&#xff0c;也多多少少看了一些文字介绍&#xff0c;多数都是对使用可视化布局拖拽&#…

[转]Docker超详细基础教程,快速入门docker

一、docker概述 1.什么是docker Docker 是一个开源的应用容器引擎&#xff0c;基于 Go 语言 并遵从 Apache2.0 协议开源。 Docker 可以让开发者打包他们的应用以及依赖包到一个轻量级、可移植的容器中&#xff0c;然后发布到任何流行的 Linux 机器上&#xff0c;也可以实现虚拟…

【Zookeeper】源码分析之服务器(一)

一、前言 前面已经介绍了Zookeeper中Leader选举的具体流程&#xff0c;接着来学习Zookeeper中的各种服务器。 二、总体框架图 对于服务器&#xff0c;其框架图如下图所示 说明&#xff1a; ZooKeeperServer&#xff0c;为所有服务器的父类&#xff0c;其请求处理链为PrepReques…