ShoppingCart 是Congo.cs中定义的一种自定义数据类型。它还伴随着BookOrder,也是在Congo.cs中定义。
ShoppingCart主要是对HashTable的包装。
它实现了一个名为_Orders的私有字段,该字段持有一个HashTable引用,ShoppingCart 还实现了一些公有方法,这些方法使BookOrder对象能够被添加到HashTable中并被删除,
ShoppingCart还实现了一个名为Orders的公共属性,该属性在HashTable的ICollection接口中可用:
aspx:


1<%@ Page Language="C#" AutoEventWireup="true" CodeFile="congo.aspx.cs" Inherits="congo" %>
2
3<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
4
5<html xmlns="http://www.w3.org/1999/xhtml" >
6<head runat="server">
7 <title>congo.comPage</title>
8</head>
9<body>
10 <h1>congo.com</h1>
11 <form id="form1" runat="server">
12 <div>
13 <table id="tbl1" width="100%" bgcolor="teal">
14 <tr>
15 <td>
16 <asp:Button ID="btn1" Text="View Cart" OnClick="OnViewCart"
17 runat="server" />
18 </td>
19 </tr>
20 </table>
21 </div>
22 <center>
23 <asp:DataGrid ID="MyDataGrid"
24 AutoGenerateColumns="false" CellPadding="2"
25 BorderWidth="1" BorderColor="lightgray"
26 Font-Names="Verdana" Font-Size="8pt"
27 GridLines="vertical" Width="90%"
28 OnItemCommand="OnItemCommand" runat="server">
29 <Columns>
30 <asp:BoundColumn HeaderText="Item ID" DataField="title_id">
31 </asp:BoundColumn>
32 <asp:BoundColumn HeaderText="Title" DataField="title">
33 </asp:BoundColumn>
34 <asp:BoundColumn HeaderText="Price" DataField="price" DataFormatString="{0:C}"
35 HeaderStyle-HorizontalAlign="center" ItemStyle-HorizontalAlign="right">
36 </asp:BoundColumn>
37 <asp:ButtonColumn HeaderText="Action" ButtonType="pushButton" Text="Add To Cart"
38 HeaderStyle-HorizontalAlign="center"
39 ItemStyle-HorizontalAlign="center" CommandName="AddToCart">
40 </asp:ButtonColumn>
41 </Columns>
42
43 <HeaderStyle BackColor="teal" ForeColor="white" Font-Bold="true" />
44 <ItemStyle BackColor="white" ForeColor="darkblue" />
45 <AlternatingItemStyle BackColor="beige" ForeColor="darkblue" />
46 </asp:DataGrid>
47 </center>
48 </form>
49</body>
50</html>
51
congo.aspx.cs:
using System;
using System.Data;
using System.Data.SqlClient;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;

public partial class congo : System.Web.UI.Page


{
protected void Page_Load(object sender, EventArgs e)

{

if (!IsPostBack)

{
string ConnectString = ConfigurationSettings.AppSettings["connectString"];
SqlDataAdapter adapter = new SqlDataAdapter("select * from titles where price!=0", ConnectString);
DataSet ds = new DataSet();
adapter.Fill(ds);
MyDataGrid.DataSource = ds;
MyDataGrid.DataBind();
}
}

//用户调用该页面并单击“AddToCart”按钮时调用该方法

/**//// <summary>
/// 该方法从DataGrid中检索产品ID及相应书籍的价格,并将
/// 它们封装到一个BookOrder对象中
/// </summary>
/// <param name="sender"></param>
/// <param name="e"></param>
protected void OnItemCommand(Object sender, DataGridCommandEventArgs e)

{
if (e.CommandName == "AddToCart")

{
//有两种方法可以得到这里的BookOrder、ShoppingCart
//1.把congo.cs放在App_Code文件夹内。
//2.把congo.cs编译成dll文件放在Bin文件夹内
//倾向于前者,便于查看Congo.cs的内容
BookOrder order =
new BookOrder(e.Item.Cells[0].Text,e.Item.Cells[1].Text,Convert.ToDecimal(e.Item.Cells[2].Text.Substring(1)),1);

//global.asax中有Session_Start,这里的SessionID????
ShoppingCart cart = (ShoppingCart)Session["MyShoppingCart"];
if (cart != null)

{
cart.AddOrder(order);
}
Response.Write("<script>alert('success to add "+e.Item.Cells[1].Text+"')</script>");
}
}

protected void OnViewCart(Object sender, EventArgs e)

{
Response.Redirect("ViewCart.aspx");
}
}

global.asax:
<%@ Application Language="C#" %>

<script runat="server">

void Application_Start(object sender, EventArgs e)

{
// Code that runs on application startup

}
void Application_End(object sender, EventArgs e)

{
// Code that runs on application shutdown

}
void Application_Error(object sender, EventArgs e)

{
// Code that runs when an unhandled error occurs

}

void Session_Start(object sender, EventArgs e)

{
//为请求页面的用户创建一个会话
Session["MyShoppingCart"] = new ShoppingCart();
// Code that runs when a new session is started

}

void Session_End(object sender, EventArgs e)

{
// Code that runs when a session ends.
// Note: The Session_End event is raised only when the sessionstate mode
// is set to InProc in the Web.config file. If session mode is set to StateServer
// or SQLServer, the event is not raised.

}
</script>

congo.cs(独立代码,在App_Code)中


using System;
using System.Collections;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;


/**//// <summary>
/// Summary description for congo
/// </summary>
public class congo


{
public congo()

{
//
// TODO: Add constructor logic here
//
}
}
[Serializable]
public class BookOrder


{
string _ItemID;
string _Title;
decimal _Price;
int _Quantity;

public string ItemID

{

get
{ return _ItemID; }

set
{ _ItemID = value; }
}

public string Title

{

get
{ return _Title; }

set
{ _Title = value; }
}

public decimal Price

{

get
{ return _Price; }

set
{ _Price = value; }
}

public int Quantity

{

get
{ return _Quantity; }

set
{ _Quantity = value; }
}

/**//// <summary>
/// 定义一个BookOrder对象,用于封装BookOrder(要买的哪些书)
/// </summary>
/// <param name="ItemID">订购的条目的ID对应数据表中的Title_ID</param>
/// <param name="Title">书的标题</param>
/// <param name="Price">价格</param>
/// <param name="Quantity">数量</param>
public BookOrder(string ItemID, string Title, decimal Price, int Quantity)

{
_ItemID = ItemID;
_Title = Title;
_Price = Price;
_Quantity = Quantity;
}
}//public class BookOrder End





[Serializable]
public class ShoppingCart


{

/**//// <summary>
/// public class Hashtable : IDictionary, ICollection
/// 位于System.Collections空间下
/// </summary>
Hashtable _Orders = new Hashtable();


/**//// <summary>
/// 定义一个只读属性,返回值类型为ICollection
/// ShoppingCart的Orders属性公开了底层HashTable的ICollection接口
/// 下面这条语句只是把HashTable的ICollection接口交给DataGrid
/// MyDataGrid.DataSource=cart.Orders;
/// ShoppingCart 和BookOrder都有Serializable特性标记。所以不论选择哪种
/// 会话状态进程模式,它们都能够被保存到会话状态中。
/// ***把打算保存到会话状态中的类型标记为可序列化的,
/// ***以便当进程模式改变时不需要修改源代码
/// </summary>
public ICollection Orders

{

get
{ return _Orders.Values; }
}


/**//// <summary>
/// 计算总的费用
/// </summary>
public decimal TotalCost

{
get

{
decimal total = 0;
//DictionaryEntry是一个struct,位于System.Collections命名空间下
foreach(DictionaryEntry entry in _Orders)

{
BookOrder order = (BookOrder)entry.Value;
total += (order.Price * order.Quantity);
}
return total;
}
}


/**//// <summary>
/// ShoppingCart中,添加订单
/// </summary>
/// <param name="Order">Order是封装了订单的BookOrder类型对象</param>
public void AddOrder(BookOrder Order)

{
//把一个HashTable转换成BookOrder
//Order.ItemID-->the Key Whose Value to Get or Set
BookOrder order = (BookOrder)_Orders[Order.ItemID];

//order 是一个特定的(ItemID)对应的order,它是一个BookOrder对象
if (order != null)

{
//如果已有该BookOrder订单项,只需要加上数量就可以了
order.Quantity += Order.Quantity;
}
else

{
//_Orders是个HashTable,HashTable有个Add方法
// Adds an element with the specified key and value into the System.Collections.Hashtable.
_Orders.Add(Order.ItemID, Order);
}
}


/**//// <summary>
/// 根据ItemID移除已经添加到购物车的条目
/// </summary>
/// <param name="ItemID">已经在购物车内的条目</param>
public void RemoveOrder(string ItemID)

{
if (_Orders[ItemID] != null)

{
//_Orders是个HashTable,HashTable有个Remove方法
_Orders.Remove(ItemID);
}
}


}//public class ShoppingCart END

ViewCart.aspx和aspx.cs:
1
<%@ Page Language="C#" AutoEventWireup="true" CodeFile="ViewCart.aspx.cs" Inherits="ViewCart" %>
2
3
4
<html xmlns="http://www.w3.org/1999/xhtml" >
5
<head runat="server">
6
<title>Untitled Page</title>
7
</head>
8
<body>
9
<form id="form1" runat="server">
10
<div>
11
<table width="100%" bgcolor="teal">
12
<tr>
13
<td>
14
<asp:Button ID="lblReturnShop" Text="Return to Shopping" OnClick="OnShop" runat="server" />
15
16
</td>
17
</tr>
18
</table>
19
</div>
20
21
<br />
22
<center>
23
<asp:DataGrid ID="MyDataGrid" AutoGenerateColumns="false" CellPadding="2"
24
BorderWidth="1" BorderColor="lightgray" Font-Names="Verdana"
25
Font-Size="8pt" GridLines="vertical" Width="90%" OnItemCommand="OnItemCommand" runat="server">
26
<Columns>
27
<asp:BoundColumn HeaderText="Item ID" DataField="ItemID">
28
</asp:BoundColumn>
29
30
<asp:BoundColumn HeaderText="Title" DataField="Title">
31
</asp:BoundColumn>
32
<asp:BoundColumn HeaderText="Price" DataField="Price" DataFormatString="{0:C}"
33
HeaderStyle-HorizontalAlign="center" ItemStyle-HorizontalAlign="right">
34
</asp:BoundColumn>
35
36
<asp:BoundColumn HeaderText="Quantity" DataField="Quantity"
37
HeaderStyle-HorizontalAlign="center" ItemStyle-HorizontalAlign="center">
38
</asp:BoundColumn>
39
<asp:ButtonColumn HeaderText="Action" Text="Remove"
40
HeaderStyle-HorizontalAlign="center" ItemStyle-HorizontalAlign="center" CommandName="RemoveFromCart">
41
</asp:ButtonColumn>
42
</Columns>
43
44
<HeaderStyle BackColor="teal" ForeColor="white" Font-Bold="true" />
45
<ItemStyle BackColor="white" ForeColor="darkblue" />
46
<AlternatingItemStyle BackColor="beige" ForeColor="darkBlue" />
47
</asp:DataGrid>
48
</center>
49
<h3><asp:Label ID="Total" runat="server"></asp:Label></h3>
50
</form>
51
</body>
52
</html>
53
ViewCart.aspx.cs:

viewCart.cs
using System;
using System.Data;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;

public partial class ViewCart : System.Web.UI.Page


{
protected void Page_Load(object sender, EventArgs e)

{
ShoppingCart cart = (ShoppingCart)Session["MyShoppingCart"];
if (cart != null)

{
MyDataGrid.DataSource = cart.Orders;
MyDataGrid.DataBind();
Total.Text = String.Format("Total Cost:{0:c}", cart.TotalCost);
}

}
protected void OnItemCommand(Object sender, DataGridCommandEventArgs e)

{
if (e.CommandName == "RemoveFromCart")

{
ShoppingCart cart = (ShoppingCart)Session["MyShoppingCart"];
if (cart != null)

{
cart.RemoveOrder(e.Item.Cells[0].Text);
MyDataGrid.DataBind();
Total.Text = String.Format("Total Cost:{0:c}", cart.TotalCost);
}

}
}
public void OnShop(object sender, EventArgs e)

{
Response.Redirect("Congo.aspx");
}
}
