📄 tab3.cpp
字号:
// Tab3.cpp : implementation file
//
#include "stdafx.h"
#include "OSDemo.h"
#include "Tab3.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CTab3 dialog
CTab3::CTab3(CWnd* pParent /*=NULL*/)
: CDialog(CTab3::IDD, pParent)
{
//{{AFX_DATA_INIT(CTab3)
//}}AFX_DATA_INIT
}
void CTab3::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CTab3)
DDX_Control(pDX, IDC_LCD, m_lcd);
DDX_Control(pDX, IDC_TAB_VIEW, m_TabView);
DDX_Control(pDX, IDC_TREE, m_wndTree);
DDX_Control(pDX, IDC_SERIAL, m_List);
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CTab3, CDialog)
//{{AFX_MSG_MAP(CTab3)
ON_BN_CLICKED(IDC_BTN_BEGIN, OnBtnBegin)
ON_WM_PAINT()
ON_NOTIFY(NM_DBLCLK, IDC_TREE, OnDblclkTree)
ON_WM_CONTEXTMENU()
ON_COMMAND(IDR_MNU_REDO2, OnMnuRedo2)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CTab3 message handlers
BOOL CTab3::OnInitDialog()
{
CDialog::OnInitDialog();
ListView_SetExtendedListViewStyle(m_List.m_hWnd, LVS_EX_FULLROWSELECT|LVS_EX_GRIDLINES);
//m_List.SetBkColor(RGB(0,0,0));
//m_List.SetTextColor(RGB(255,207,156));
m_List.InsertColumn(0,"页号",LVCFMT_LEFT,40);
m_List.InsertColumn(1,"FIFO",LVCFMT_CENTER,40);
m_List.InsertColumn(2,"OPT",LVCFMT_CENTER,40);
m_List.InsertColumn(3,"LRU",LVCFMT_CENTER,40);
m_TabView.AddPage("平均命中图", &TabPage1, IDD_TAB_PAGE1);
m_TabView.AddPage("具体情况图", &TabPage2, IDD_TAB_PAGE2);
m_TabView.Show();
HTREEITEM Root = m_wndTree.InsertItem ( _T("请求页式管理"),0,1 );
HTREEITEM hti1 = m_wndTree.InsertItem ( _T("请双击'开始测试'按钮"),0,1,Root );
m_wndTree.Expand(Root,TVE_EXPAND);
m_lcd.SetNumberOfLines(5);
m_lcd.SetXCharsPerLine(18);
m_lcd.SetSize(CMatrixStatic::TINY);
m_lcd.SetDisplayColors(RGB(165, 181, 66), RGB(0, 0, 0), RGB(148, 156, 66));
m_lcd.AdjustClientXToSize(18);
m_lcd.AdjustClientYToSize(5);
m_lcd.SetText(_T(" PROGRAM MADE BY WUJUN 9800134 SouthEast University "));
m_lcd.DoScroll(1000, CMatrixStatic::UP);
UpdateData(false);
return TRUE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
float CTab3::rnd()
{
float n;
n=rand()/(float)32767;
return n;
}
void CTab3::OnBtnBegin()
{
((CButton*)GetDlgItem(IDC_BTN_BEGIN))->SetWindowText("重 做 实 验? @_@");
InitMem();
int i,j,k;
bool bFIFO=false,bOPT=false,bLRU=false;
for (int n=0;n<4;n++) //虚存容量分别为1k、2k、4k、8k。
{
for (j=0;j<VPageItem[n].VMemItem.GetSize();j++) //当虚存页面容量一定(1k-8k),遍历所有可能的物理内存页面数
{
InitMemStack();
for (i=0;i<20;i++) //当虚存容量和物理页面数一定,遍历访问序列数组
{
//MessageBox("FIFO");
for (k=0;k<FIFOStack.GetSize();k++) //扫描FIFO看是否命中。
{
if (VPageItem[n].VMemItem[j].Serial[i].PageID==FIFOStack[k].PageID)
{
VPageItem[n].VMemItem[j].Serial[i].bFIFO=true;
VPageItem[n].VMemItem[j].FIFORate+=5;
FIFOStack[k].UseTime=i; //记录使用时间为第j个访问序列
bFIFO=true;
}
}
if (!bFIFO) //fifo没有命中,且内存物理页面数已到最大。置换最先进入的页面。
{ //如果内存物理页面数未到最大,就增加一个页面
VPageItem[n].VMemItem[j].Serial[i].bFIFO=false;
if(FIFOStack.GetSize()>=VPageItem[n].VMemItem[j].PageSize)
FIFOStack.RemoveAt(0); //删掉最先进入的页面
MEMSTACK newStack1;
newStack1.PageID=VPageItem[n].VMemItem[j].Serial[i].PageID;
newStack1.UseTime=i;
FIFOStack.Add(newStack1); //加入刚刚访问到的页面
}
bFIFO=false;
//MessageBox("OPT");
for (k=0;k<OPTStack.GetSize();k++) //扫描OPT看是否命中。
{
if (VPageItem[n].VMemItem[j].Serial[i].PageID==OPTStack[k].PageID)
{
VPageItem[n].VMemItem[j].Serial[i].bOPT=true;
VPageItem[n].VMemItem[j].OPTRate+=5;
OPTStack[k].UseTime=i;
OPTStack[k].NextSame=VPageItem[n].VMemItem[j].Serial[i].NextSame;//记录使用时间为第j个访问序列
bOPT=true;
}
}
if (!bOPT) //OPT没有命中,且内存物理页面数已到最大。置换最先进入的页面。
{ //如果内存物理页面数未到最大,就增加一个页面
int maxTime,DelPos;
DelPos=0;
VPageItem[n].VMemItem[j].Serial[i].bOPT=false;
if(OPTStack.GetSize()>=VPageItem[n].VMemItem[j].PageSize)
{
maxTime=OPTStack[0].NextSame;
for (int x=0;x<OPTStack.GetSize();x++)
{
if (OPTStack[x].NextSame>=maxTime)
{
maxTime=OPTStack[x].NextSame;
DelPos=x;
}
}
OPTStack.RemoveAt(DelPos);
}//OPTStack.RemoveAt(0); //删掉最先进入的页面
MEMSTACK newStack2;
newStack2.PageID=VPageItem[n].VMemItem[j].Serial[i].PageID;
newStack2.UseTime=i;
newStack2.NextSame=VPageItem[n].VMemItem[j].Serial[i].NextSame;
OPTStack.Add(newStack2); //加入刚刚访问到的页面
}
bOPT=false;
for (k=0;k<LRUStack.GetSize();k++) //扫描LRU看是否命中。
{
if (VPageItem[n].VMemItem[j].Serial[i].PageID==LRUStack[k].PageID)
{
VPageItem[n].VMemItem[j].Serial[i].bLRU=true;
VPageItem[n].VMemItem[j].LRURate+=5;
LRUStack[k].UseTime=i; //记录使用时间为第j个访问序列
bLRU=true;
}
}
if (!bLRU) //LRU没有命中,且内存物理页面数已到最大。置换时间最长的页面。
{ //如果内存物理页面数未到最大,就增加一个页面
VPageItem[n].VMemItem[j].Serial[i].bLRU=false;
if(LRUStack.GetSize()>=VPageItem[n].VMemItem[j].PageSize)
{
int minTime,RemovePos;
RemovePos=0;
minTime=LRUStack[0].UseTime;
for(int x=0;x<LRUStack.GetSize();x++)
{
if(LRUStack[x].UseTime<=minTime)
{
minTime=LRUStack[x].UseTime;
RemovePos=x;
}
}
LRUStack.RemoveAt(RemovePos); //删掉最久没有使用的页面
}
MEMSTACK newStack3;
newStack3.PageID=VPageItem[n].VMemItem[j].Serial[i].PageID;
newStack3.UseTime=i;
LRUStack.Add(newStack3); //加入刚刚访问到的页面
}
bLRU=false;
}
VPageItem[n].AveFIFORate+=VPageItem[n].VMemItem[j].FIFORate/VPageItem[n].VMemItem.GetSize();
VPageItem[n].AveOPTRate+=VPageItem[n].VMemItem[j].OPTRate/VPageItem[n].VMemItem.GetSize();
VPageItem[n].AveLRURate+=VPageItem[n].VMemItem[j].LRURate/VPageItem[n].VMemItem.GetSize();
}
}
ShowMemList(2,0);
ShowGraph1();
m_TabView.SetCurSel(0);
CRect rect;
((CButton*)GetDlgItem(IDC_TREE))->GetWindowRect(&rect);
CPoint pt;
pt.x=180;
pt.y=150;
ShowBallTip(pt,"展开并单击项目查看详细命中情况");
}
void CTab3::AddPageItem(CString PageID, CString FIFO, CString OPT, CString LRU)
{
LVITEM lvitem;
int iActualItem;
for(int iSubItem=0;iSubItem<6;iSubItem++)
{
lvitem.mask = LVIF_TEXT|(iSubItem == 0? LVIF_IMAGE : 0);
lvitem.iItem = (iSubItem == 0)? ++PageCount : iActualItem;
lvitem.iSubItem = iSubItem;
CString CurTime;
switch(iSubItem)
{
case 0:
lvitem.pszText =(LPTSTR)(LPCTSTR)PageID;
break;
case 1:
lvitem.pszText =(LPTSTR)(LPCTSTR)FIFO;
break;
case 2:
lvitem.pszText =(LPTSTR)(LPCTSTR)OPT;
break;
case 3:
lvitem.pszText =(LPTSTR)(LPCTSTR)LRU;
break;
}
if (iSubItem == 0)
iActualItem = m_List.InsertItem(&lvitem);
else
m_List.SetItem(&lvitem);
}
}
void CTab3::OnPaint()
{
CPaintDC dc(this); // device context for painting
// Do not call CDialog::OnPaint() for painting messages
}
void CTab3::InitMem()
{
int n,i,j,k;
CStatic a;
::ZeroMemory(VPageItem,sizeof(VPageItem));
TabPage1.bDraw=false;
CString CurRnd,CurChar;
m_wndTree.DeleteAllItems();
HTREEITEM Root = m_wndTree.InsertItem ( _T("随机访问序列实验结果"),0,1 );
for (n=0;n<4;n++)
{
int maxPage=32/(int)pow(2,n);
VPageItem[n].vPageSize=(int)pow(2,n);
VPageItem[n].AveFIFORate=0;
VPageItem[n].AveLRURate=0;
VPageItem[n].AveOPTRate=0;
CString NodeStr;
NodeStr.Format("页面大小为%dK",VPageItem[n].vPageSize);
VPageItem[n].hti=m_wndTree.InsertItem ( NodeStr,0,1,Root );
srand((unsigned)::GetTickCount());
for (i=4;i<=maxPage;i++)
{
MEMITEM newItem;
newItem.PageSize=i;
newItem.FIFORate=0;
newItem.OPTRate=0;
newItem.LRURate=0;
NodeStr.Format("物理内存块分%d页",i);
newItem.hti=m_wndTree.InsertItem ( NodeStr,0,1,VPageItem[n].hti);
for(j=0;j<20;j++) //生成20个随机访问序列
{
newItem.PageSize=i;
newItem.Serial[j].bFIFO=false;
newItem.Serial[j].bOPT=false;
newItem.Serial[j].bLRU=false;
newItem.Serial[j].PageID=(UINT)((float)maxPage*rnd());
}
for(j=0;j<20;j++) //得到序列中和本页面号相同的下一序列的下标号
{
k=j+1;
while(newItem.Serial[j].PageID!=newItem.Serial[k].PageID && k<20)
{ k++;}
if(k>=20)
newItem.Serial[j].NextSame=100;
else
newItem.Serial[j].NextSame=k;
}
VPageItem[n].VMemItem.Add(newItem);
}
}
m_wndTree.Expand(Root,TVE_EXPAND);
}
void CTab3::ShowMemList(int nPage,int nMem)
{
m_List.DeleteAllItems();
CString strPageID;
CString Check1;
CString Check2;
CString Check3;
for(int i=0;i<20;i++)
{
strPageID.Format("%d",VPageItem[nPage].VMemItem[nMem].Serial[i].PageID);
if (VPageItem[nPage].VMemItem[nMem].Serial[i].bFIFO) Check1="√";
else Check1="×";
if (VPageItem[nPage].VMemItem[nMem].Serial[i].bOPT) Check2="√";
else Check2="×";
if (VPageItem[nPage].VMemItem[nMem].Serial[i].bLRU) Check3="√";
else Check3="×";
AddPageItem(strPageID,Check1,Check2,Check3);
}
}
void CTab3::InitMemStack()
{
FIFOStack.RemoveAll();
LRUStack.RemoveAll();
OPTStack.RemoveAll();
}
void CTab3::ShowGraph1()
{
for(int n=0;n<4;n++)
{
TabPage1.potOPT[n].rate=(int)VPageItem[n].AveOPTRate;
TabPage1.potFIFO[n].rate=(int)VPageItem[n].AveFIFORate;
TabPage1.potLRU[n].rate=(int)VPageItem[n].AveLRURate;
}
TabPage1.m_Draw.ShowWindow(SW_HIDE);
TabPage1.m_Draw.ShowWindow(SW_SHOW);
TabPage1.DrawBar();
TabPage1.bDraw=true;
}
void CTab3::OnDblclkTree(NMHDR* pNMHDR, LRESULT* pResult)
{
int i,j;
for (i=0;i<4;i++)
{
for (j=0;j<VPageItem[i].VMemItem.GetSize();j++)
{
if (m_wndTree.GetSelectedItem()==VPageItem[i].VMemItem[j].hti)
{
ShowMemList(i,j);
ShowGraph2(i);
m_lcd.StopScroll();
CString disp;
disp.Format("PAGESIZE=%2dKB MEM PAGENUM= %2d FIFO HitRate;%2d%% OPT HitRate;%2d%% LRU HitRate;%2d%% ",VPageItem[i].VMemItem[j].PageSize,VPageItem[i].VMemItem.GetSize(),(int)VPageItem[i].VMemItem[j].FIFORate,(int)VPageItem[i].VMemItem[j].OPTRate,(int)VPageItem[i].VMemItem[j].LRURate);
m_lcd.SetText(disp);
m_TabView.SetCurSel(1);
}
}
}
//
*pResult = 0;
}
void CTab3::ShowGraph2(int nPage)
{
int j;
TabPage1.bDraw=false;
TabPage2.bDraw=false;
if (m_TabView.GetCurSel()==0)
{
TabPage1.ShowWindow(SW_HIDE);
TabPage1.ShowWindow(SW_SHOW);
}
else
{
TabPage2.ShowWindow(SW_HIDE);
TabPage2.ShowWindow(SW_SHOW);
}
TabPage2.potFIFO.RemoveAll();
TabPage2.potOPT.RemoveAll();
TabPage2.potLRU.RemoveAll();
TabPage1.bDraw=true;
TabPage2.bDraw=true;
for(j=0;j<VPageItem[nPage].VMemItem.GetSize();j++)
{
POTS FIFOPot,OPTPot,LRUPot;
FIFOPot.rate=(int)VPageItem[nPage].VMemItem[j].FIFORate;
OPTPot.rate=(int)VPageItem[nPage].VMemItem[j].OPTRate;
LRUPot.rate=(int)VPageItem[nPage].VMemItem[j].LRURate;
TabPage2.potFIFO.Add(FIFOPot);
TabPage2.potOPT.Add(OPTPot);
TabPage2.potLRU.Add(LRUPot);
}
TabPage2.Draw3dLine();
}
void CTab3::OnContextMenu(CWnd* pWnd, CPoint point)
{
if (point.x == -1 && point.y == -1){
//keystroke invocation
CRect rect;
GetClientRect(rect);
ClientToScreen(rect);
point = rect.TopLeft();
point.Offset(5, 5);
}
CMenu menu;
VERIFY(menu.LoadMenu(IDR_POP_MNU2));
CMenu* pPopup = menu.GetSubMenu(0);
ASSERT(pPopup != NULL);
CWnd* pWndPopupOwner = this;
//while (pWndPopupOwner->GetStyle() & WS_CHILD)
// pWndPopupOwner = pWndPopupOwner->GetParent();
TrackSkinPopupMenu( pPopup->m_hMenu, TPM_LEFTALIGN | TPM_RIGHTBUTTON, point.x, point.y,
pWndPopupOwner->m_hWnd );
}
void CTab3::OnMnuRedo2()
{
OnBtnBegin();
}
void CTab3::ShowBallTip(CPoint pt, CString msg)
{
LOGFONT lf;
::ZeroMemory (&lf, sizeof (lf));
lf.lfHeight = 15;
lf.lfWeight = FW_BOLD;
lf.lfUnderline = FALSE;
::strcpy (lf.lfFaceName, _T("楷体_GB2312"));
// Get the edit box co-ordinates in screen co-ordinates
//CRect rect;
//((CStatic*)hwnd)->GetWindowRect(&rect);
// Point where the balloon will be show, middle of edit box
//CPoint pt = rect.CenterPoint();
m_pBalloonTip = CBalloonTip::Show(pt, CSize(250, 100), msg, lf, 5, TRUE);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -