对VC 一些常见问题的整理

C/C++ 专栏收录该内容
78 篇文章 0 订阅
 

(1)为什么某个类突然在工作区间里面突然看不见了?

只是类隐藏了,打开FILEVIEW,找到隐藏类的头文件,随便敲一下键盘的空格键,类就会在CLASSVIEW中显示了

(2)在基于对话框的程序中,一按回车键,对话框就没了。

把确定按纽的缺省属性前面的对勾去掉,重载OnOk()函数,在OnOk()函数里注释掉调用基类的OnOk()函数那行代码

(3) 为什么我的VC6.0自动显示成员列表功能时有时无?
删除该项目扩展名为.ncb文件,重新打开该项目。

(4)孙老师的视频教程第一课的程序,为什么在我机子上不行?

选菜单project->settings...在弹出的对话框中选Link,在最下边有Project Options,把里边的/subsystem:console删除就可以了

(5)如何干净的删除一个类?

先从workspace中的fileview中删除对应的.h和.cpp文件;再关闭项目,从实际的文件夹中删除对应的.h和.cpp文件;再删除.clw文件。 最后打开项目,rebuild all。

(6)网络编程一课中的聊天室程序在为什么老是绑定失败?

一般这种问题是端口设置在6000监听,正好和QQ的端口冲突,多换几个端口试试就可以了

(7)网络程序只能在debug运行,release不行,提示错误 error LNK2001: unresolved external symbol __imp__WSAStartup@8

在Release下仍然需要添加Ws2_32.lib。

(8)我画了一条直线但是当窗口最大化时或者被其他窗口覆盖时,直线不见了,只剩下直线原先存在的窗口

这是因为窗口重绘,你可以在响应WM_PAINT的OnDraw()函数中添加画线的代码

(9)在安装VC时未安装MSDN, 自己再用MSDN安装盘安装后在VC中按F1无法调用?

修改注册表是最直接的方法,具体过程如下: 在HKEY_CURRENT_USER/Software/Microsoft/DevStudio/6.0/Help下增加Enable,Filename,State三个主键,注意其类型,含义如下:  Enable 类型:DWORD,默认值是1,改变为0x00000001  Filename 类型:字符串改为c:program files....MSDev98helpMsdev.hlp  State 类型:DWORD 默认值为0,改变为0x00000001

(10)如何在应用程序中打开一个超级链接?

这个问题实际上很简单,只要使用ShellExecute API函数就行了

(11)如何在没安装VC的环境下的机器也能打开运行用MFC编写的程序?

把编译模式改为RELEASE,然后点工程-》设置-》常规,选择使用MFC作为静态连接库

(12)如何自定义一个消息?

1.#define WM_MY_MESSAGE  WM_USER+1;2.头文件DECLARE_MESSAGE_MAP()前写消息响应函数原形;3.在 BEGIN_MESSAGE_MAP添加消息到函数的映射.4.写函数的实现部分

(13)怎样改变VC++编辑器默认的颜色?

工具—》选择—》格式,选中注释的颜色即可改变。

(14)复制了一段代码到当前工作空间里,可是代码排列很乱,如何调整?

简单,按下鼠标左键拖动鼠标将代码选择上,同时按下键盘的ALT+F8键

(15) _T("Option 1"),_T()是什么意思?为什么要转换,直接用不可以?

  _T()自动将()内字符串转成unicode or Multibyte-character or SBCS (ASCII) 根据系统宏定义,为了将程序与vb等unicode 编码的程序交互,为了程序的国际化,为了..

(16)如何改变视图的背景色?

你可以通过处理WM_ERASEBKGND消息来改变CView、CFrameWnd或CWnd对象的背景色

(17)如何建立多文档?

为了加入对附加文档类型的支持,你可以在CWinApp派生类中创建和注册附加CmultiDocTemplate对象。。将一个附加文档类型加入到MFC程序的一般步骤如下:
用AppWizard来创建一个新的文档类和视图类。
用资源编辑器增加新的资源字串来支持新的文档类。要想知道关于文档样板字符串格式的更多内容,请参阅"如何理解文档样板字符串"。

用资源编辑器增加附加的应用程序图标和菜单资源。注意,这些资源中每一个的ID都必须与在步骤2中创建的文档模板字符串的ID是相同的。这个ID被CmultiDocTemplate类用来识别与附加文档类型相关的资源。

在应用程序的InitInstance()函数中,创建了另一个CMultiDocTemplate对象并且用CWinApp::AddDocTemplate()函数来注册。例如:

CMultiDocTemplate* pDocTemplate2 = new CMultiDocTemplate(
  IDR_DOC2TYPE, RUNTIME_CLASS(CDoc2),
  RUNTIME_CLASS(CMDIChildWnd),RUNTIME_CLASS(CView2));
  AddDocTemplate(pDocTemplate2);

最后,将定制的序列化和绘图代码加入到你的新文档和视图类中。

(18)如何使我的程序在启动时不创建一个新文档?
在程序的InitInstance中的ProcessShellCommand函数之前加入: cmdInfo.m_nShellCommand = CCommandLineInf:FileNothing

(19) 如何获取应用程序的实例句柄?
应用程序的实例句柄保存在CWinApp m_hInstance 中,可以这么调用AfxGetInstanceHandle获得句柄.

(20)如何得到程序中其它类的指针(例如框架类,视类,文档类等等)?

请看此贴:

[转帖]MFC应用程序中指针的使用

(21)为什么创建类的时候我不能直接生成从CDialogBar派生的类?

ClassVizard的确没有提供这个功能,要从没有提供的类派生类的时候只能通过手动修改来完成

(22)我用classwizard 给静态文本框加变量时,为什么里面没有它的ID??

因为所有的静态文本控件的ID都被默认为了IDC_STATIC,你只需要修改这个ID号就可以了

(23)获得各种目录信息
Windows目录: Use "GetWindowsDirectory"
Windows下的system目录: Use "GetSystemDirectory"
temp目录: Use "GetTempPath"
当前目录: Use "GetCurrentDirectory"

(24)如果让控制台应用程序支持MFC类库?
    可以在控制台应用程序中include 来引入mfc库,但是控制台应用程序缺省是单线程的,mfc是多线程的,为解决该矛盾,在project setting->c/c++ 选项,选择code generation,在use run-time library 下拉框中选择debug multithread。

(25) 我怎样才能在我的应用程序中循环浏览已经打开的文档?

使用CDocTemplate中未公开的GetFirstDocPosition()和GetNextDoc()函数。

(26)才能在我的应用程序中循环浏览已经打开的视?

使 用 CDocument 中 未 公 开 的 GetFirstViewPosition() 和 GetNextView() 函 数。

(27)数PreCreateWindow是干什么用的?

PreCreateWindow 允 许 你 在 调 用 CreateWindow 之 前 来 改 变 窗 口 属 性。

(28)该怎样防止MFC在窗口标题栏上把文档名预置成应用程序名?

在 PreCreateWindow 函 数 中 删 除 FWS_PREFIXTITLE 标 志 的 窗 口 样 式:

    cs.style &= ~FWS_PREFIXTITLE;

(29) 我应该怎样防止MFC在窗口标题栏上添加文档名?

在 PreCreateWindow 函 数 中 删 除 FWS_ADDTOTITLE 标 志 的 窗 口 样 式:

    cs.style &= ~FWS_ADDTOTITLE ;

(30) 我应该如何改变视窗口的大小?

因 为 视 窗 口 实 际 上 是 框 架 窗 口 的 子 窗 口,所 以 你 必 须 改 变 框 架 窗 口 的 大 小,而 不 是 改 变 视 窗 口。使 用 CView 类 中 的 GetParentFrame() 函 数 获 得 指 向 框 架 窗 口 的 指 针,然 后 调 用 MoveWindow() 函 数 来 改 变 框 架 的 大 小。这 会 使 变 尺 寸 的 视 充 满 框 架 窗 口。

(31) 我有一无模式对话框。我怎样才能在窗口退出时删除CDialog对象?

把“delete this”加 到 PostNcDestroy 中。这 主 要 用 在 需 要 自 动 删 除 对 象 的 场 合。

(32) 为什么把“delete this”放在PostNcDestroy中而不是OnNcDestroy?

OnNcDestroy 只 被 已 建 立 的 窗 口 调 用。如 果 建 立 窗 口 失 败 ( 如 PreCreateWindow ),则 没 有 窗 口 处 来 发 送 WM_NCDESTROY 消 息。PostNcDestroy 是 在 对 象 窗 口 被 完 全 删 除,在 OnNcDestroy 后,甚 至 在 窗 口 建 立 失 败 之 后 调 用 的。

(33):如何为一个MFC应用程序添加ODBC功能?

(1)在文件Stdafx.h文件末尾添加下面一行:

#include // MFC ODBC database classes

(2)在文本模式下编辑RC文件(利用File->Open As text 方式)

在下面的程序行(共有两处)

#include "l.chsafxprint.rc" // printing/print preview resources

添加下一行:

#include "l.chsafxdb.rc" // Database resources

(34):数据库表修改后,如何快速更新一个绑定到表的CrecordSet记录集?

利用ClassWizard 中 Member Variables标签下选中记录集类后,利用UpdateColoumns和Bind All。

(35):怎么才能让窗口最大化显示啊? 我在框架的PreCreateWindow中 cs.styles|=WS_MAXIMIZE 不行啊, OnCreate 中 SetWindowLong(m_hWnd,GWL_STYLE,WS_MAXIMIZE);也不行啊

上面两种方法都不行,要是窗口最大化显示,应改变ShowWindow()的参数,

在InitInstance()中将

m_pMainWnd->ShowWindow(...)改为

m_pMainWnd->ShowWindow(SW_SHOWMAXINIZE);就Ok

(36)怎么把别人程序中设计好的对话框放到自己的程序中??

用VC打开自己的程序,选择资源视图;然后点FILE->OPEN菜单项,打开设计好的对话框的资源文件(后缀名为。RC),这里注意一定只打开后缀名为。RC的资源文件,然后在VC编辑器的文档区域就会有你刚打开的另一个程序的资源文件中资源的一个树型结构图,然后找到你要复制的对话框资源ID,鼠标左键按住ID号,然后拖放到资源视图中,这个时候你再看看自己程序的资源视图,是不是已经复制过来了。罗嗦了这么多,其实问题的关键是在一个编辑器中同时打开自己的项目和另一个项目的资源文件。

(37)[求助]急!!!关于installshield制作中的注册表问题

我用installshield 制作安装程序,怎样在注册表中写入用户单位的名称,请大家帮帮忙啊

在InstallShield选择Resources,在其中的Registry Entry部分输入要添加的注册项 。

(38) VC6下如何对程序进行调试
  
在主菜单"Build"中,有一个Start Build的子菜单,它下面包含了Go菜单(快捷键为F5),选择后,程序将从当前语句进入调试运行,直到遇到断点或程序结束。将鼠标移动到要调试的代码行,单击鼠标右键选择“Insert/Remove Breakpoint”,或者按下F9,可以在该行上添加断点,此时断点代码行前面出现一个棕色的圈,再次选择将清除断点。进入调试状态后,Debug菜单将取代Build菜单出现在菜单栏中,它下面包含常用的调试操作,如Step Over,单步运行并不跟踪到调用的函数内部;其他还包括Step Into,Step Out, Stop Debugging等调试方法。

(39)简介对话框应用程序中UpdateData函数的作用及其参数含义与使用场合。
  UpdateData只有一个BOOL类型的参数,UpdateData(FALSE)一般用于对话框控件连接的变量值刷新屏幕显示;UpdateData(TRUE)用于获取屏幕数据到对话框控件连接的变量中。

(40)、如何单击除了窗口标题栏以外的区域使窗口移动

当窗口需要确定鼠标位置时Windows向窗口发送WM_NCHITTEST信息,可以处理 该信息使Windows认为鼠标在窗口标题上。对于对话框和基于对话的应用程序,可 以使用ClassWizard处理该信息并调用基类函数,如果函数返回HTCLIENT 则表明 鼠标在客房区域,返回HTCAPTION表明鼠标在Windows的标题栏中。

UINT CSampleDialog : : OnNcHitTest (Cpoint point )

{

UINT nHitTest =Cdialog: : OnNcHitTest (point );

return (nHitTest = =HTCLIENT)? HTCAPTION : nHitTest ;

}

上述技术有两点不利之处,其一是在窗口的客户区域双击时, 窗口将极大; 其二,它不适合包含几个视窗的主框窗口。还有一种方法,当用户按下鼠标左键 使主框窗口认为鼠标在其窗口标题上,使用ClassWizard在视窗中处理WM_LBUTTODOWN 信息并向主框窗口发送一个WM_NCLBUTTONDOWN信息和一个单击测试HTCAPTION

void CSampleView : : OnLButtonDown (UINT nFlags , Cpoint point )

{

CView : : OnLButtonDow (nFlags , pont );

//Fool frame window into thinking somene clicked on

its caption bar .

GetParentFrame ( ) > PostMessage (

WM_NCLBUTTONDOWN , HTCAPTION , MAKELPARAM (poitn .x , point .y) );

}

该技术也适用于对话框和基于对的应用程序,只是不必调用CWnd : : GetParentFrame

void CSampleDialog : : OnLbuttonDown (UINT nFlags, Cpoint point )

{

Cdialog : : OnLButtonDow (nFlags, goint ); //Fool dialog into thinking simeone clicked on its caption bar . PostMessage (WM_NCLBUTTONDOWN , HTCAPTION , MAKELPARM (point.x , point. y ) )

[转帖]MFC应用程序中指针的使用

分类:默认栏目

MFC应用程序中指针的使用
作者:gouguijia

1) 在View中获得Doc指针 2) 在App中获得MainFrame指针 3) 在View中获得MainFrame指针 4) 获得View(已建立)指针 5) 获得当前文档指针 6) 获得状态栏与工具栏指针 7) 获得状态栏与工具栏变量 8) 在Mainframe获得菜单指针 9) 在任何类中获得应用程序类 10) 从文档类取得视图类的指针(1) 11) 在App中获得文档模板指针 12) 从文档模板获得文档类指针 13) 在文档类中获得文档模板指针 14) 从文档类取得视图类的指针(2) 15) 从一个视图类取得另一视图类的指针

VC中编程对于刚刚开始学习的同学,最大的障碍和问题就是消息机制和指针获取与操作。其实这些内容基本上是每本VC学习工具书上必讲的内容,而且通过MSDN很多问题都能解决。
下面文字主要是个人在编程中指针使用的一些体会,说的不当的地方请指正。
一般我们使用的框架是VC提供的Wizard生成的MFC App Wizard(exe)框架,无论是多文档还是单文档,都存在指针获取和操作问题。
下面这节内容主要是一般的框架,然后再讲多线程中的指针使用。使用到的类需要包含响应的头文件。首先一般获得本类(视,文档,对话框都支持)实例指针this,用this的目的,主要可以通过类中的函数向其他类或者函数中发指针,以便于在非本类中操作和使用本类中的功能。

1) 在View中获得Doc指针
CYouSDIDoc *pDoc=GetDocument();一个视只能有一个文档。
2) 在App中获得MainFrame指针
CWinApp 中的 m_pMainWnd变量就是MainFrame的指针
也可以:
CMainFrame *pMain =(CMainFrame *)AfxGetMainWnd();
3) 在View中获得MainFrame指针
CMainFrame *pMain=(CmaimFrame *)AfxGetApp()->m_pMainWnd;
4) 获得View(已建立)指针
CMainFrame *pMain=(CmaimFrame *)AfxGetApp()->m_pMainWnd;
CyouView *pView=(CyouView *)pMain->GetActiveView();
5) 获得当前文档指针
CDocument * pCurrentDoc =(CFrameWnd *)m_pMainWnd->GetActiveDocument();
6) 获得状态栏与工具栏指针
CStatusBar * pStatusBar=(CStatusBar *)AfxGetMainWnd()->GetDescendantWindow(AFX_IDW_STATUS_BAR);
CToolBar * pToolBar=(CtoolBar *)AfxGetMainWnd()->GetDescendantWindow(AFX_IDW_TOOLBAR);
7) 如果框架中加入工具栏和状态栏变量还可以这样
(CMainFrame *)GetParent()->m_wndToolBar;
(CMainFrame *)GetParent()->m_wndStatusBar;
8) 在Mainframe获得菜单指针
CMenu *pMenu=m_pMainWnd->GetMenu();
9) 在任何类中获得应用程序类
用MFC全局函数AfxGetApp()获得。

10) 从文档类取得视图类的指针
我是从 http://download.cqcnc.com/soft/program/article/vc/vc405.html学到的,从文档获得视图类指针目的一般为了控制同一文档的多个视图的定位问题,我的体会特别是文字处理CEditView当产生多个视图类时,这个功能是非常需要的。
CDocument类提供了两个函数用于视图类的定位:
GetFirstViewPosition()和GetNextView()
virtual POSITION GetFirstViewPosition() const;
virtual CView* GetNextView(POSITION& rPosition) const;

注意:GetNextView()括号中的参数用的是引用方式,因此执行后值可能改变。
GetFirstViewPosition()用于返回第一个视图位置(返回的并非视图类指针,而是一个POSITION类型值),GetNextView()有两个功能:返回下一个视图类的指针以及用引用调用的方式来改变传入的POSITION类型参数的值。很明显,在Test程序中,只有一个视图类,因此只需将这两个函数调用一次即可得到CTestView的指针如下(需定义一个POSITION结构变量来辅助操作):
CTestView* pTestView;
POSITION pos=GetFirstViewPosition();
pTestView=GetNextView(pos);
这样,便可到了CTestView类的指针pTestView.执行完几句后,变量pos=NULL,因为没有下一个视图类,自然也没有下一个视图类的POSITION.但是这几条语句太简单,不具有太强的通用性和安全特征;当象前面说的那样,当要在多个视图为中返回某个指定类的指针时,我们需要遍历所有视图类,直到找到指定类为止。判断一个类指针指向的是否某个类的实例时,可用IsKindOf()成员函数时行检查,如:
pView->IsKindOf(RUNTIME_CLASS(CTestView));
即可检查pView所指是否是CTestView类。

有了以上基础,我们已经可以从文档类取得任何类的指针。为了方便,我们将其作为一个文档类的成员函数,它有一个参数,表示要获得哪个类的指针。实现如下:
CView* CTestDoc::GetView(CRuntimeClass* pClass)
{
 CView* pView;
 POSITION pos=GetFirstViewPosition();

 while(pos!=NULL){
  pView=GetNextView(pos);
  if(!pView->IsKindOf(pClass))
  break;
 }

 if(!pView->IsKindOf(pClass)){
  AfxMessageBox("Connt Locate the View.rn http://www.VCKBASE.com");
  return NULL;
 }

 return pView;
}

其中用了两次视图类的成员函数IsKindOf()来判断,是因为退出while循环有三种可能:

1.pos为NULL,即已经不存在下一个视图类供操作;
2.pView已符合要求。

1和2同是满足。这是因为GetNextView()的功能是将当前视图指针改变成一个视图的位置同时返回当前视图指针,因此pos是pView的下一个视图类的POSITION,完全有可能既是pos==NULL又是pView符合需要。当所需的视图是最后一个视图是最后一个视图类时就如引。因此需采用两次判断。
使用该函数应遵循如下格式(以取得CTestView指针为例):
CTestView* pTestView=(CTestView*)GetView(RUNTIME_CLASS(CTestView));
RUNTIME_CLASS是一个宏,可以简单地理解它的作用:将类的名字转化为CRuntimeClass为指针。
至于强制类型转换也是为了安全特性考虑的,因为从同一个基类之间的指针类型是互相兼容的。这种强制类型转换也许并不必要,但能避免一些可能出现的麻烦。

3.从一个视图类取得另一视图类的指针 综合1和2,很容易得出视图类之间互相获得指针的方法:就是用文档类作中转,先用1的方法得到文档类的指针,再用2的方法,以文档类的视图定位函数取得另一个视图类。同样,可以实现成一个函数:
(假设要从CTestAView中取得指向其它视图类的指针)
CView* CTestAView::GetView(CRuntimeClass* pClass)
{
 CTestDoc* pDoc=(CTestDoc*)GetDocument();
 CView* pView;
 POSITION pos=pDoc->GetFirstViewPosition();
 while(pos!=NULL){
  pView=pDoc->GetNextView(pos);
  if(!pView->IsKindOf(pClass))
  break;
 }
 if(!pView->IsKindOf(pClass)){
  AfxMessageBox("Connt Locate the View.");
  return NULL;
 }

 return pView;
}
这个函数和2中的GetView()相比,一是多了第一句以取得文档类指针,二是在GetFirstViewPosition()和GetNextView()前加上了文档类指针,以表示它们是文档类成员函数。
有了此函数;当要从CTestAView中取得CTestBView的指针时,只需如下:
CTestBView* pTestbView=(CTestView*)GetView(RUNTIME_CLASS(CTestBView));
11)对于单文档中也可以加入多个文档模板,但是一般的开发就使用MDI方式开发多文档模板,其方法与上述视图的获取方法很接近,这里稍做解释,如果不清楚,请查阅MSDN,(以下四个内容(11、12、13、14)来源: http://sanjianxia.myrice.com/vc/vc45.htm

可以用CWinApp::GetFirstDocTemplatePostion获得应用程序注册的第一个文档模板的位置;
利用该值来调用CWinApp::GetNextDocTemplate函数,获得第一个CDocTemplate对象指针。
POSITION GetFirstDocTemplate( ) const; 
CDocTemplate *GetNextDocTemplate( POSITION & pos ) const;
第二个函数返回由pos 标识的文档模板。POSITION是MFC定义的一个用于迭代或对象指针检索的值。通过这两个函数,应用程序可以遍历整个文档模板列表。如果被检索的文档模板是模板列表中的最后一个,则pos参数被置为NULL。

12)一个文档模板可以有多个文档,每个文档模板都保留并维护了一个所有对应文档的指针列表。
用CDocTemplate::GetFirstDocPosition函数获得与文档模板相关的文档集合中第一个文档的位置,并用POSITION值作为CDocTemplate::GetNextDoc的参数来重复遍历与模板相关的文档列表。函数原形为:
viaual POSITION GetFirstDocPosition( ) const = 0; 
visual CDocument *GetNextDoc(POSITION & rPos) const = 0;  
如果列表为空,则rPos被置为NULL.

13)在文档中可以调用CDocument::GetDocTemplate获得指向该文档模板的指针。函数原形如下:
CDocTemplate * GetDocTemplate ( ) const; 
如果该文档不属于文档模板管理,则返回值为NULL。

14)一个文档可以有多个视。每一个文档都保留并维护一个所有相关视的列表。CDocument::AddView将一个视连接到文档上,将该视加入到文档相联系的视的列表中,并将视的文档指针指向该文档。当有File/New、File/Open、Windows/New或Window/Split的命令而将一个新创建的视的对象连接到文档上时, MFC会自动调用该函数,框架通过文档/视的结构将文档和视联系起来。当然,程序员也可以根据自己的需要调用该函数。
Virtual POSITION GetFirstViewPosition( ) const; 
Virtual CView * GetNextView( POSITION &rPosition) cosnt;
应用程序可以调用CDocument::GetFirstViewPosition返回与调用文档相联系的视的列表中的第一个视的位置,并调用CDocument::GetNextView返回指定位置的视,并将rPositon的值置为列表中下一个视的POSITION值。如果找到的视为列表中的最后一个视,则将rPosition置为NULL.

15)从一个视图类取得另一视图类的指针
这个应用在多视的应用程序中很多见,一般如果自己在主程序或者主框架中做好变量记号,也可以获得,还有比较通用的就是用文档类作中转,以文档类的视图遍历定位,取得另一个视图类。这个功能从本文第10项中可以得到。

这些资料大部分都是从网上和MSDN中获得的,写这个文档就是为了让大家不用再寻找,列出标题,可操作性更强。

SQL语句

分类:默认栏目

SQL语句

下列语句部分是Mssql语句,不可以在access中使用。
 
SQL分类:   DDL—数据定义语言(CREATE,ALTER,DROP,DECLARE)
DML—数据操纵语言(SELECT,DELETE,UPDATE,INSERT)
DCL—数据控制语言(GRANT,REVOKE,COMMIT,ROLLBACK)  
首先,简要介绍基础语句:  
1、说明:创建数据库CREATE DATABASE database-name   
2、说明:删除数据库drop database dbname  
3、说明:备份sql server  
--- 创建 备份数据的 deviceUSE master
EXEC sp_addumpdevice 'disk', 'testBack', 'c:mssql7backupMyNwind_1.dat'  
--- 开始 备份BACKUP DATABASE pubs TO testBack   
4、说明:
创建新表create table tabname(col1 type1 [not null] [primary key],col2 type2 [not null],..)  
根据已有的表创建新表:
A:create table tab_new like tab_old (使用旧表创建新表)
B:create table tab_new as select col1,col2… from tab_old definition only  
5、说明:  
删除新表:drop table tabname   
6、说明:  
增加一个列:Alter table tabname add column col type  注:列增加后将不能删除。DB2中列加上后数据类型也不能改变,唯一能改变的是增加varchar类型的长度。  
7、说明:
  添加主键:Alter table tabname add primary key(col)
  说明:
  删除主键:Alter table tabname drop primary key(col)  
8、说明:
  创建索引:create [unique] index idxname on tabname(col….)
  删除索引:drop index idxname  注:索引是不可更改的,想更改必须删除重新建。  
9、说明:
  创建视图:create view viewname as select statement
  删除视图:drop view viewname  
10、说明:几个简单的基本的sql语句
  选择:select * from table1 where 范围
  插入:insert into table1(field1,field2) values(value1,value2)
  删除:delete from table1 where 范围
  更新:update table1 set field1=value1 where 范围
  查找:select * from table1 where field1 like ’%value1%’ ---like的语法很精妙,查资料!
  排序:select * from table1 order by field1,field2 [desc]
  总数:select count * as totalcount from table1
  求和:select sum(field1) as sumvalue from table1
  平均:select avg(field1) as avgvalue from table1
  最大:select max(field1) as maxvalue from table1
  最小:select min(field1) as minvalue from table1  
11、说明:几个高级查询运算词
  A: UNION 运算符
  UNION 运算符通过组合其他两个结果表(例如 TABLE1 和 TABLE2)并消去表中任何重复行而派生出一个结果表。当 ALL 随 UNION 一起使用时(即 UNION ALL),不消除重复行。两种情况下,派生表的每一行不是来自 TABLE1 就是来自 TABLE2。
  B: EXCEPT 运算符
  EXCEPT 运算符通过包括所有在 TABLE1 中但不在 TABLE2 中的行并消除所有重复行而派生出一个结果表。当 ALL 随 EXCEPT 一起使用时 (EXCEPT ALL),不消除重复行。
  C: INTERSECT 运算符
  INTERSECT 运算符通过只包括 TABLE1 和 TABLE2 中都有的行并消除所有重复行而派生出一个结果表。当 ALL 随 INTERSECT 一起使用时 (INTERSECT ALL),不消除重复行。  注:使用运算词的几个查询结果行必须是一致的。  

12、说明:使用外连接
  A、left outer join:
  左外连接(左连接):结果集几包括连接表的匹配行,也包括左连接表的所有行。 SQL: select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.c
  B:right outer join:
  右外连接(右连接):结果集既包括连接表的匹配连接行,也包括右连接表的所有行。
  C:full outer join:
  全外连接:不仅包括符号连接表的匹配行,还包括两个连接表中的所有记录。
  其次,大家来看一些不错的sql语句
  1、说明:复制表(只复制结构,源表名:a 新表名:b) (Access可用)
  法一:select * into b from a where 1<>1
  法二:select top 0 * into b from a
  2、说明:拷贝表(拷贝数据,源表名:a 目标表名:b) (Access可用)insert into b(a, b, c) select d,e,f from b;
  3、说明:跨数据库之间表的拷贝(具体数据使用绝对路径) (Access可用)insert into b(a, b, c) select d,e,f from b in ‘具体数据库’ where 条件  例子:..from b in '"&Server.MapPath(".")&"data.mdb" &"' where..
  4、说明:子查询(表名1:a 表名2:b)select a,b,c from a where a IN (select d from b ) 或者: select a,b,c from a where a IN (1,2,3)
  5、说明:显示文章、提交人和最后回复时间select a.title,a.username,b.adddate from table a,(select max(adddate) adddate from table where table.title=a.title) b  6、说明:外连接查询(表名1:a 表名2:b)select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.c
  7、说明:在线视图查询(表名1:a )select * from (SELECT a,b,c FROM a) T where t.a > 1;
  8、说明:between的用法,between限制查询数据范围时包括了边界值,not between不包括select * from table1 where time between time1 and time2select a,b,c, from table1 where a not between 数值1 and 数值2
  9、说明:in 的使用方法select * from table1 where a [not] in (‘值1’,’值2’,’值4’,’值6’)
  10、说明:两张关联表,删除主表中已经在副表中没有的信息 delete from table1 where not exists ( select * from table2 where table1.field1=table2.field1 )
  11、说明:四表联查问题:select * from a left inner join b on a.a=b.b right inner join c on a.a=c.c inner join d on a.a=d.d where .....
  12、说明:日程安排提前五分钟提醒SQL: select * from 日程安排 where datediff('minute',f开始时间,getdate())>5
  13、说明:一条sql 语句搞定数据库分页select top 10 b.* from (select top 20 主键字段,排序字段 from 表名 order by 排序字段 desc) a,表名 b where b.主键字段 = a.主键字段 order by a.排序字段
  14、说明:前10条记录select top 10 * form table1 where 范围
  15、说明:选择在每一组b值相同的数据中对应的a最大的记录的所有信息(类似这样的用法可以用于论坛每月排行榜,每月热销产品分析,按科目成绩排名,等等.)select a,b,c from tablename ta where a=(select max(a) from tablename tb where tb.b=ta.b)
  16、说明:包括所有在 TableA 中但不在 TableB和TableC 中的行并消除所有重复行而派生出一个结果表(select a from tableA ) except (select a from tableB) except (select a from tableC)
  17、说明:随机取出10条数据select top 10 * from tablename order by newid()
  18、说明:随机选择记录select newid()
  19、说明:删除重复记录Delete from tablename where id not in (select max(id) from tablename group by col1,col2,...)
  20、说明:列出数据库里所有的表名select name from sysobjects where type='U'
  21、说明:列出表里的所有的select name from syscolumns where id=object_id('TableName')
  22、说明:列示type、vender、pcs字段,以type字段排列,case可以方便地实现多重选择,类似select 中的case。select type,sum(case vender when 'A' then pcs else 0 end),sum(case vender when 'C' then pcs else 0 end),sum(case vender when 'B' then pcs else 0 end) FROM tablename group by type
  显示结果:type vender pcs
电脑 A 1
电脑 A 1
光盘 B 2
光盘 A 2
手机 B 3
手机 C 3
  23、说明:初始化表table1TRUNCATE TABLE table1
  24、说明:选择从10到15的记录select top 5 * from (select top 15 * from table order by id asc) table_别名 order by id desc
  随机选择数据库记录的方法(使用Randomize函数,通过SQL语句实现)
  对存储在数据库中的数据来说,随机数特性能给出上面的效果,但它们可能太慢了些。你不能要求ASP“找个随机数”然后打印出来。实际上常见的解决方案是建立如下所示的循环:
Randomize

RNumber = Int(Rnd*499) +1
 
While Not objRec.EOF

If objRec("ID") = RNumber THEN

... 这里是执行脚本 ...

end if

objRec.MoveNext

Wend   
这很容易理解。首先,你取出1到500范围之内的一个随机数(假设500就是数据库内记录的总数)。然后,你遍历每一记录来测试ID 的值、检查其是否匹配RNumber。满足条件的话就执行由THEN 关键字开始的那一块代码。假如你的RNumber 等于495,那么要循环一遍数据库花的时间可就长了。虽然500这个数字看起来大了些,但相比更为稳固的企业解决方案这还是个小型数据库了,后者通常在一个数据库内就包含了成千上万条记录。这时候不就死定了?   
采用SQL,你就可以很快地找出准确的记录并且打开一个只包含该记录的recordset,如下所示:
Randomize

RNumber = Int(Rnd*499) + 1

 
SQL = "SELECT * FROM Customers WHERE ID = " & RNumber

 
set objRec = ObjConn.Execute(SQL)

Response.WriteRNumber & " = " & objRec("ID") & " " & objRec("c_email")
  不必写出RNumber 和ID,你只需要检查匹配情况即可。只要你对以上代码的工作满意,你自可按需操作“随机”记录。Recordset没有包含其他内容,因此你很快就能找到你需要的记录这样就大大降低了处理时间。
  再谈随机数  
现在你下定决心要榨干Random 函数的最后一滴油,那么你可能会一次取出多条随机记录或者想采用一定随机范围内的记录。把上面的标准Random 示例扩展一下就可以用SQL应对上面两种情况了。
  为了取出几条随机选择的记录并存放在同一recordset内,你可以存储三个随机数,然后查询数据库获得匹配这些数字的记录:
  SQL = "SELECT * FROM Customers WHERE ID = " & RNumber & " OR ID = " & RNumber2 & " OR ID = " & RNumber3
  假如你想选出10条记录(也许是每次页面装载时的10条链接的列表),你可以用BETWEEN 或者数学等式选出第一条记录和适当数量的递增记录。这一操作可以通过好几种方式来完成,但是 SELECT 语句只显示一种可能(这里的ID 是自动生成的号码):

SQL = "SELECT * FROM Customers WHERE ID BETWEEN " & RNumber & " AND " & RNumber & "+ 9"
  注意:以上代码的执行目的不是检查数据库内是否有9条并发记录。
  随机读取若干条记录,测试过Access语法:
SELECT top 10 * From 表名 ORDER BY Rnd(id)

Sql server:select top n * from 表名 order by newid()

mysql select * From 表名 Order By rand() Limit n  
Access左连接语法(最近开发要用左连接,Access帮助什么都没有,网上没有Access的SQL说明,只有自己测试, 现在记下以备后查)
  语法 select table1.fd1,table1,fd2,table2.fd2 From table1 left join table2 on table1.fd1,table2.fd1 where ...
  使用SQL语句 用...代替过长的字符串显示
  语法:
  SQL数据库:select case when len(field)>10 then left(field,10)+'...' else field end as news_name,news_id from tablename

  Access数据库:SELECT iif(len(field)>2,left(field,2)+'...',field) FROM tablename;
  Conn.Execute说明 
 Execute方法  
该方法用于执行SQL语句。根据SQL语句执行后是否返回记录集,该方法的使用格式分为以下两种:
  1.执行SQL查询语句时,将返回查询得到的记录集。
用法为:  Set 对象变量名=连接对象.Execute("SQL 查询语言")
  Execute方法调用后,会自动创建记录集对象,并将查询结果存储在该记录对象中,通过Set方法,将记录集赋给指定的对象保存,以后对象变量就代表了该记录集对象。
  2.执行SQL的操作性语言时,没有记录集的返回。
此时用法为:  连接对象.Execute "SQL 操作性语句" [, RecordAffected][, Option] 
 ·RecordAffected 为可选项,此出可放置一个变量,SQL语句执行后,所生效的记录数会自动保存到该变量中。通过访问该变量,就可知道SQL语句队多少条记录进行了操作。
  ·Option 可选项,该参数的取值通常为adCMDText,它用于告诉ADO,应该将Execute方法之后的第一个字符解释为命令文本。通过指定该参数,可使执行更高效。
  ·BeginTrans、RollbackTrans、CommitTrans方法  这三个方法是连接对象提供的用于事务处理的方法。BeginTrans用于开始一个事物;RollbackTrans用于回滚事务;
CommitTrans用于提交所有的事务处理结果,即确认事务的处理。
  事务处理可以将一组操作视为一个整体,只有全部语句都成功执行后,事务处理才算成功;若其中有一个语句执行失败,则整个处理就算失败,并恢复到处里前的状态。

  BeginTrans和CommitTrans用于标记事务的开始和结束,在这两个之间的语句,就是作为事务处理的语句。判断事务处理是否成功,可通过连接对象的Error集合来实现,若Error集合的成员个数不为0,则说明有错误发生,事务处理失败。Error集合中的每一个Error对象,代表一个错误信息。

精妙SQL语句整理2007-01-08 13:08一、基础

1、说明:创建数据库
CREATE DATABASE database-name
2、说明:删除数据库
drop database dbname
3、说明:备份sql server
--- 创建 备份数据的 device
USE master
EXEC sp_addumpdevice 'disk', 'testBack', 'c:mssql7backupMyNwind_1.dat'
--- 开始 备份
BACKUP DATABASE pubs TO testBack
4、说明:创建新表
create table tabname(col1 type1 [not null] [primary key],col2 type2 [not null],..)
根据已有的表创建新表:
A:create table tab_new like tab_old (使用旧表创建新表)
B:create table tab_new as select col1,col2… from tab_old definition only
5、说明:删除新表
drop table tabname
6、说明:增加一个列
Alter table tabname add column col type
注:列增加后将不能删除。DB2中列加上后数据类型也不能改变,唯一能改变的是增加varchar类型的长度。
7、说明:添加主键: Alter table tabname add primary key(col)
说明:删除主键: Alter table tabname drop primary key(col)
8、说明:创建索引:create [unique] index idxname on tabname(col….)
删除索引:drop index idxname
注:索引是不可更改的,想更改必须删除重新建。
9、说明:创建视图:create view viewname as select statement
删除视图:drop view viewname
10、说明:几个简单的基本的sql语句
选择:select * from table1 where 范围
插入:insert into table1(field1,field2) values(value1,value2)
删除:delete from table1 where 范围
更新:update table1 set field1=value1 where 范围
查找:select * from table1 where field1 like ’%value1%’ ---like的语法很精妙,查资料!
排序:select * from table1 order by field1,field2 [desc]
总数:select count as totalcount from table1
求和:select sum(field1) as sumvalue from table1
平均:select avg(field1) as avgvalue from table1
最大:select max(field1) as maxvalue from table1
最小:select min(field1) as minvalue from table1
11、说明:几个高级查询运算词
A: UNION 运算符
UNION 运算符通过组合其他两个结果表(例如 TABLE1 和 TABLE2)并消去表中任何重复行而派生出一个结果表。当 ALL 随 UNION 一起使用时(即 UNION ALL),不消除重复行。两种情况下,派生表的每一行不是来自 TABLE1 就是来自 TABLE2。
B: EXCEPT 运算符
EXCEPT 运算符通过包括所有在 TABLE1 中但不在 TABLE2 中的行并消除所有重复行而派生出一个结果表。当 ALL 随 EXCEPT 一起使用时 (EXCEPT ALL),不消除重复行。
C: INTERSECT 运算符
INTERSECT 运算符通过只包括 TABLE1 和 TABLE2 中都有的行并消除所有重复行而派生出一个结果表。当 ALL 随 INTERSECT 一起使用时 (INTERSECT ALL),不消除重复行。
注:使用运算词的几个查询结果行必须是一致的。
12、说明:使用外连接
A、left outer join:
左外连接(左连接):结果集几包括连接表的匹配行,也包括左连接表的所有行。
SQL: select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.c
B:right outer join:
右外连接(右连接):结果集既包括连接表的匹配连接行,也包括右连接表的所有行。
C:full outer join:
全外连接:不仅包括符号连接表的匹配行,还包括两个连接表中的所有记录。

二、提升

1、说明:复制表(只复制结构,源表名:a 新表名:b) (Access可用)
法一:select * into b from a where 1<>1
法二:select top 0 * into b from a

2、说明:拷贝表(拷贝数据,源表名:a 目标表名:b) (Access可用)
insert into b(a, b, c) select d,e,f from b;

3、说明:跨数据库之间表的拷贝(具体数据使用绝对路径) (Access可用)
insert into b(a, b, c) select d,e,f from b in ‘具体数据库’ where 条件
例子:..from b in '"&Server.MapPath(".")&"data.mdb" &"' where..

4、说明:子查询(表名1:a 表名2:b)
select a,b,c from a where a IN (select d from b ) 或者: select a,b,c from a where a IN (1,2,3)

5、说明:显示文章、提交人和最后回复时间
select a.title,a.username,b.adddate from table a,(select max(adddate) adddate from table where table.title=a.title) b

6、说明:外连接查询(表名1:a 表名2:b)
select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.c

7、说明:在线视图查询(表名1:a )
select * from (SELECT a,b,c FROM a) T where t.a > 1;

8、说明:between的用法,between限制查询数据范围时包括了边界值,not between不包括
select * from table1 where time between time1 and time2
select a,b,c, from table1 where a not between 数值1 and 数值2

9、说明:in 的使用方法
select * from table1 where a [not] in (‘值1’,’值2’,’值4’,’值6’)

10、说明:两张关联表,删除主表中已经在副表中没有的信息
delete from table1 where not exists ( select * from table2 where table1.field1=table2.field1 )

11、说明:四表联查问题:
select * from a left inner join b on a.a=b.b right inner join c on a.a=c.c inner join d on a.a=d.d where .....

12、说明:日程安排提前五分钟提醒
SQL: select * from 日程安排 where datediff('minute',f开始时间,getdate())>5

13、说明:一条sql 语句搞定数据库分页
select top 10 b.* from (select top 20 主键字段,排序字段 from 表名 order by 排序字段 desc) a,表名 b where b.主键字段 = a.主键字段 order by a.排序字段

14、说明:前10条记录
select top 10 * form table1 where 范围

15、说明:选择在每一组b值相同的数据中对应的a最大的记录的所有信息(类似这样的用法可以用于论坛每月排行榜,每月热销产品分析,按科目成绩排名,等等.)
select a,b,c from tablename ta where a=(select max(a) from tablename tb where tb.b=ta.b)

16、说明:包括所有在 TableA 中但不在 TableB和TableC 中的行并消除所有重复行而派生出一个结果表
(select a from tableA ) except (select a from tableB) except (select a from tableC)

17、说明:随机取出10条数据
select top 10 * from tablename order by newid()

18、说明:随机选择记录
select newid()

19、说明:删除重复记录
Delete from tablename where id not in (select max(id) from tablename group by col1,col2,...)

20、说明:列出数据库里所有的表名
select name from sysobjects where type='U'

21、说明:列出表里的所有的
select name from syscolumns where id=object_id('TableName')

22、说明:列示type、vender、pcs字段,以type字段排列,case可以方便地实现多重选择,类似select 中的case。
select type,sum(case vender when 'A' then pcs else 0 end),sum(case vender when 'C' then pcs else 0 end),sum(case vender when 'B' then pcs else 0 end) FROM tablename group by type
显示结果:
type vender pcs
电脑 A 1
电脑 A 1
光盘 B 2
光盘 A 2
手机 B 3
手机 C 3

23、说明:初始化表table1

TRUNCATE TABLE table1

24、说明:选择从10到15的记录
select top 5 * from (select top 15 * from table order by id asc) table_别名 order by id desc

三、技巧

1、1=1,1=2的使用,在SQL语句组合时用的较多

“where 1=1” 是表示选择全部 “where 1=2”全部不选,
如:
if @strWhere !=''
begin
set @strSQL = 'select count(*) as Total from [' + @tblName + '] where ' + @strWhere
end
else
begin
set @strSQL = 'select count(*) as Total from [' + @tblName + ']'
end

我们可以直接写成
set @strSQL = 'select count(*) as Total from [' + @tblName + '] where 1=1 安定 '+ @strWhere

2、收缩数据库
--重建索引
DBCC REINDEX
DBCC INDEXDEFRAG
--收缩数据和日志
DBCC SHRINKDB
DBCC SHRINKFILE

3、压缩数据库
dbcc shrinkdatabase(dbname)

4、转移数据库给新用户以已存在用户权限
exec sp_change_users_login 'update_one','newname','oldname'
go

5、检查备份集
RESTORE VERIFYONLY from disk='E:dvbbs.bak'

6、修复数据库
ALTER DATABASE [dvbbs] SET SINGLE_USER
GO
DBCC CHECKDB('dvbbs',repair_allow_data_loss) WITH TABLOCK
GO
ALTER DATABASE [dvbbs] SET MULTI_USER
GO

7、日志清除
SET NOCOUNT ON
DECLARE @LogicalFileName sysname,
@MaxMinutes INT,
@NewSize INT


USE tablename -- 要操作的数据库名
SELECT @LogicalFileName = 'tablename_log', -- 日志文件名
@MaxMinutes = 10, -- Limit on time allowed to wrap log.
@NewSize = 1 -- 你想设定的日志文件的大小(M)

-- Setup / initialize
DECLARE @OriginalSize int
SELECT @OriginalSize = size
FROM sysfiles
WHERE name = @LogicalFileName
SELECT 'Original Size of ' + db_name() + ' LOG is ' +
CONVERT(VARCHAR(30),@OriginalSize) + ' 8K pages or ' +
CONVERT(VARCHAR(30),(@OriginalSize*8/1024)) + 'MB'
FROM sysfiles
WHERE name = @LogicalFileName
CREATE TABLE DummyTrans
(DummyColumn char (8000) not null)


DECLARE @Counter INT,
@StartTime DATETIME,
@TruncLog VARCHAR(255)
SELECT @StartTime = GETDATE(),
@TruncLog = 'BACKUP LOG ' + db_name() + ' WITH TRUNCATE_ONLY'

DBCC SHRINKFILE (@LogicalFileName, @NewSize)
EXEC (@TruncLog)
-- Wrap the log if necessary.
WHILE @MaxMinutes > DATEDIFF (mi, @StartTime, GETDATE()) -- time has not expired
AND @OriginalSize = (SELECT size FROM sysfiles WHERE name = @LogicalFileName)
AND (@OriginalSize * 8 /1024) > @NewSize
BEGIN -- Outer loop.
SELECT @Counter = 0
WHILE ((@Counter BEGIN -- update
INSERT DummyTrans VALUES ('Fill Log')
DELETE DummyTrans
SELECT @Counter = @Counter + 1
END
EXEC (@TruncLog)
END
SELECT 'Final Size of ' + db_name() + ' LOG is ' +
CONVERT(VARCHAR(30),size) + ' 8K pages or ' +
CONVERT(VARCHAR(30),(size*8/1024)) + 'MB'
FROM sysfiles
WHERE name = @LogicalFileName
DROP TABLE DummyTrans
SET NOCOUNT OFF

8、说明:更改某个表
exec sp_changeobjectowner 'tablename','dbo'

9、存储更改全部表

CREATE PROCEDURE dbo.User_ChangeObjectOwnerBatch
@OldOwner as NVARCHAR(128),
@NewOwner as NVARCHAR(128)
AS

DECLARE @Name as NVARCHAR(128)
DECLARE @Owner as NVARCHAR(128)
DECLARE @OwnerName as NVARCHAR(128)

DECLARE curObject CURSOR FOR
select 'Name' = name,
'Owner' = user_name(uid)
from sysobjects
where user_name(uid)=@OldOwner
order by name

OPEN curObject
FETCH NEXT FROM curObject INTO @Name, @Owner
WHILE(@@FETCH_STATUS=0)
BEGIN
if @Owner=@OldOwner
begin
set @OwnerName = @OldOwner + '.' + rtrim(@Name)
exec sp_changeobjectowner @OwnerName, @NewOwner
end
-- select @name,@NewOwner,@OldOwner

FETCH NEXT FROM curObject INTO @Name, @Owner
END

close curObject
deallocate curObject
GO


10、SQL SERVER中直接循环写入数据
declare @i int
set @i=1
while @ibegin
insert into test (userid) values(@i)
set @i=@i+1
end

小记存储过程中经常用到的本周,本月,本年函数
Dateadd(wk,datediff(wk,0,getdate()),-1)
Dateadd(wk,datediff(wk,0,getdate()),6)

Dateadd(mm,datediff(mm,0,getdate()),0)
Dateadd(ms,-3,dateadd(mm,datediff(m,0,getdate())+1,0))

Dateadd(yy,datediff(yy,0,getdate()),0)
Dateadd(ms,-3,DATEADD(yy, DATEDIFF(yy,0,getdate())+1, 0))

上面的SQL代码只是一个时间段
Dateadd(wk,datediff(wk,0,getdate()),-1)
Dateadd(wk,datediff(wk,0,getdate()),6)
就是表示本周时间段.
下面的SQL的条件部分,就是查询时间段在本周范围内的:
Where Time BETWEEN Dateadd(wk,datediff(wk,0,getdate()),-1) AND Dateadd(wk,datediff(wk,0,getdate()),6)
而在存储过程中
select @begintime = Dateadd(wk,datediff(wk,0,getdate()),-1)
select @endtime = Dateadd(wk,datediff(wk,0,getdate()),6)

最后,再补充一些:

分组group

  常用于统计时,如分组查总数:
select gender,count(sno)
from students
group by gender
(查看男女学生各有多少)

  注意:从哪种角度分组就从哪列"group by"

  对于多重分组,只需将分组规则罗列。比如查询各届各专业的男女同学人数 ,那么分组规则有:届别(grade)、专业(mno)和性别(gender),所以有"group by grade, mno, gender"

select grade, mno, gender, count(*)
from students
group by grade, mno, gender

  通常group还和having联用,比如查询1门课以上不及格的学生,则按学号(sno)分类有:

select sno,count(*) from grades
where markgroup by sno
having count(*)>1

  6.UNION联合

  合并查询结果,如:

SELECT * FROM students
WHERE name like ‘张%’
UNION [ALL]
SELECT * FROM students
WHERE name like ‘李%’

  7.多表查询

  a.内连接

select g.sno,s.name,c.coursename
from grades g JOIN students s ON g.sno=s.sno
JOIN courses c ON g.cno=c.cno
(注意可以引用别名)
b.外连接
b1.左连接
select courses.cno,max(coursename),count(sno)
from courses LEFT JOIN grades ON courses.cno=grades.cno
group by courses.cno

  左连接特点:显示全部左边表中的所有项目,即使其中有些项中的数据未填写完全。

  左外连接返回那些存在于左表而右表中却没有的行,再加上内连接的行。

  b2.右连接

  与左连接类似

  b3.全连接

select sno,name,major
from students FULL JOIN majors ON students.mno=majors.mno

  两边表中的内容全部显示

  c.自身连接

select c1.cno,c1.coursename,c1.pno,c2.coursename
from courses c1,courses c2 where c1.pno=c2.cno

  采用别名解决问题。

  d.交叉连接

select lastname+firstname from lastname CROSS JOIN firstanme

huawei

分类:默认栏目

1、局部变量能否和全局变量重名?  

 答:能,局部会屏蔽全局。要用全局变量,需要使用"::"   局部变量可以与全局变量同名,在函数内引用这个变量时,会用到同名的局部变量,而不会用到全局变量。对于有些编译器而言,在同一个函数内可以定义多个同名的局部变量,比如在两个循环体内都定义一个同名的局部变量,而那个局部变量的作用域就在那个循环体内。  

2、如何引用一个已经定义过的全局变量?   

答:extern   可以用引用头文件的方式,也可以用extern关键字,如果用引用头文件方式来引用某个在头文件中声明的全局变理,假定你将那个变写错了,那么在编译期间会报错,如果你用extern方式引用时,假定你犯了同样的错误,那么在编译期间不会报错,而在连接期间报错。

3、全局变量可不可以定义在可被多个.C文件包含的头文件中?为什么?  

 答:可以,在不同的C文件中以static形式来声明同名全局变量。   可以在不同的C文件中声明同名的全局变量,前提是其中只能有一个C文件中对此变量赋初值,此时连接不会出错   

 7、static全局变量与普通的全局变量有什么区别?static局部变量和普通局部变量有什么区别?static函数与普通函数有什么区别?   

全局变量(外部变量)的说明之前再冠以static 就构成了静态的全局变量。全局变量本身就是静态存储方式, 静态全局变量当然也是静态存储方式。 这两者在存储方式上并无不同。这两者的区别虽在于非静态全局变量的作用域是整个源程序, 当一个源程序由多个源文件组成时,非静态的全局变量在各个源文件中都是有效的。 而静态全局变量则限制了其作用域, 即只在定义该变量的源文件内有效, 在同一源程序的其它源文件中不能使用它。由于静态全局变量的作用域局限于一个源文件内,只能为该源文件内的函数公用, 因此可以避免在其它源文件中引起错误。   从以上分析可以看出, 把局部变量改变为静态变量后是改变了它的存储方式即改变了它的生存期。把全局变量改变为静态变量后是改变了它的作用域, 限制了它的使用范围。   static函数与普通函数作用域不同。仅在本文件。只在当前源文件中使用的函数应该说明为内部函数(static),内部函数应该在当前源文件中说明和定义。对于可在当前源文件以外使用的函数,应该在一个头文件中说明,要使用这些函数的源文件要包含这个头文件   static全局变量与普通的全局变量有什么区别:static全局变量只初使化一次,防止在其他文件单元中被引用;   static局部变量和普通局部变量有什么区别:static局部变量只被初始化一次,下一次依据上一次结果值;   static函数与普通函数有什么区别:static函数在内存中只有一份,普通函数在每个被调用中维持一份拷贝   

 8、程序的局部变量存在于(堆栈)中,全局变量存在于(静态区 )中,动态申请数据存在于( 堆)中。   

 9、设有以下说明和定义:   typedef union {long i; int k[5]; char c;} DATE;   struct data { int cat; DATE cow; double dog;} too;   DATE max;   则语句 printf("%d",sizeof(struct date)+sizeof(max));的执行结果是:___52____   答:DATE是一个union, 变量公用空间. 里面最大的变量类型是int[5], 占用20个字节. 所以它的大小是20 data是一个struct, 每个变量分开占用空间. 依次为int4 + DATE20 + double8 = 32. 所以结果是 20 + 32 = 52.   当然...在某些16位编辑器下, int可能是2字节,那么结果是 int2 + DATE10 + double8 = 20   

11、写出下列代码的输出内容  

  #include   

 int inc(int a)   

 {     return(++a);    }   

int multi(int*a,int*b,int*c)   

 {     return(*c=*a**b);    }  

  typedef int(FUNC1)(int in);   

 typedef int(FUNC2) (int*,int*,int*);   

 void show(FUNC2 fun,int arg1, int*arg2)   

 {     INCp=&inc;    

 int temp =p(arg1);   

  fun(&temp,&arg1, arg2);  

   printf("%dn",*arg2);    }  

  main()   

 {     int a;  

   show(multi,10,&a);  

   return 0;   

 }   

答:110   

 12、请找出下面代码中的所以错误   说明:以下代码是把一个字符串倒序,如“abcd”倒序后变为“dcba”    1、#include"string.h"    2、main()    3、{    4、 char*src="hello,world";    5、 char* dest=NULL;    6、 int len=strlen(src);    7、 dest=(char*)malloc(len);    8、 char* d=dest;    9、 char* s=src[len];    10、 while(len--!=0)    11、 d++=s--;    12、 printf("%s",dest);    13、 return 0;    14、}

    答:   方法1:    int main()    {    char* src = "hello,world";    int len = strlen(src);    char* dest = (char*)malloc(len+1);//要为分配一个空间    char* d = dest;    char* s = &src[len-1];//指向最后一个字符    while( len-- != 0 )     *d++=*s--;    *d = 0;//尾部要加    printf("%sn",dest);    free(dest);// 使用完,应当释放空间,以免造成内存汇泄露    return 0;   }

方法2:    #include    #include   main()   {      char str[]="hello,world";    int len=strlen(str);    char t;    for(int i=0; i    #include    int main(void)    { long l;    char *str = "98765432";   l = atol(lstr);    printf("string = %s integer = %ldn", str, l);   return(0);   }   

13.对于一个频繁使用的短小函数,在C语言中应用什么实现,在C++中应用什么实现?   c用宏定义,c++用inline  

14.直接链接两个信令点的一组链路称作什么?   PPP点到点连接     

15.接入网用的是什么接口?    

16.voip都用了那些协议?  

17.软件测试都有那些种类?  

 黑盒:针对系统功能的测试   白合:测试函数功能,各函数接口  

18.确定模块的功能和模块的接口是在软件设计的那个队段完成的?   概要设计阶段  

 19.   enum string  {    x1,    x2,    x3=10,    x4,    x5,   }x;   问x= 0x801005,0x8010f4 ;  

 20.   unsigned char *p1;   unsigned long *p2;   p1=(unsigned char *)0x801000;   p2=(unsigned long *)0x810000;   请问p1+5= ;     p2+5= ;   选择题:   

21.Ethternet链接到Internet用到以下那个协议?   A.HDLC;B.ARP;C.UDP;D.TCP;E.ID  

 22.属于网络层协议的是:      A.TCP;B.IP;C.ICMP;D.X.25  

    

24.  unsigned short hash(unsigned short key)   {  return (key>>)%256  }   请问hash(16),hash(256)的值分别是:    A.1.16;B.8.32;C.4.16;D.

找错题:  

  25.请问下面程序有什么错误?    int a[60][250][1000],i,j,k;   for(k=0;kMax_GT_Length)    {     return GT_Length_ERROR;   }    ....... }    问答题:   

 29.IP Phone的原理是什么?   IPV6   

 30.TCP/IP通信建立的过程怎样,端口有什么作用?   三次握手,确定是哪个应用程序使用该协议   

31.1号信令和7号信令有什么区别,我国某前广泛使用的是那一种?   

 32.列举5种以上的电话新业务

华为笔试题

分类:默认栏目

1.写出判断ABCD四个表达式的是否正确, 若正确, 写出经过表达式中 a的值(3分)
int a = 4;
(A)a += (a++); (B) a += (++a) ;(C) (a++) += a;(D) (++a) += (a++);
a = ?
答:C错误,左侧不是一个有效变量,不能赋值,可改为(++a) += a;
改后答案依次为9,10,10,11

前++可看作一个变量;后++看做固定值。

如++(++a)可以,而(a++)++不行。

2.某32位系统下, C++程序,请计算sizeof 的值(5分).
char str[] = “http://www.ibegroup.com/”
char *p = str ;
int n = 10;
请计算
sizeof (str ) = ?(1)
sizeof ( p ) = ?(2)
sizeof ( n ) = ?(3)
void Foo ( char str[100]){
请计算
sizeof( str ) = ?(4)
}
void *p = malloc( 100 );
请计算
sizeof ( p ) = ?(5)
答:(1)17 (2)4 (3) 4 (4)4 (5)4

3. 回答下面的问题. (4分)
(1).头文件中的 ifndef/define/endif 干什么用?预处理
答:防止头文件被重复引用
(2). #include <filename.h> 和 #include "filename.h" 有什么区别?
答:前者用来包含开发环境提供的库头文件,后者用来包含自己编写的头文件。
(3).在C++ 程序中调用被 C 编译器编译后的函数,为什么要加 extern “C”声明?
答:函数和变量被C++编译后在符号库中的名字与C语言的不同,被extern "C"修饰的变
量和函数是按照C语言方式编译和连接的。由于编译后的名字不同,C++程序不能直接调
用C 函数。C++提供了一个C 连接交换指定符号extern“C”来解决这个问题。
(4). switch()中不允许的数据类型是?
答:实型

4. 回答下面的问题(6分)
(1).Void GetMemory(char **p, int num){
*p = (char *)malloc(num);
}
void Test(void){
char *str = NULL;
GetMemory(&str, 100);
strcpy(str, "hello");
printf(str);
}
请问运行Test 函数会有什么样的结果?
答:输出“hello”
(2). void Test(void){
char *str = (char *) malloc(100);
strcpy(str, “hello”);
free(str);
if(str != NULL){
strcpy(str, “world”);
printf(str);
}
}
请问运行Test 函数会有什么样的结果?
答:输出“world”
(3). char *GetMemory(void){
char p[] = "hello world";
return p;
}
void Test(void){
char *str = NULL;
str = GetMemory();
printf(str);
}
请问运行Test 函数会有什么样的结果?
答:无效的指针,输出不确定

5. 编写strcat函数(6分)
已知strcat函数的原型是char *strcat (char *strDest, const char *strSrc);
其中strDest 是目的字符串,strSrc 是源字符串。
(1)不调用C++/C 的字符串库函数,请编写函数 strcat
答:
VC源码:
char * __cdecl strcat (char * dst, const char * src)
{
char * cp = dst;
while( *cp )
cp++; /* find end of dst */
while( *cp++ = *src++ ) ; /* Copy src to end of dst */
return( dst ); /* return dst */
}
(2)strcat能把strSrc 的内容连接到strDest,为什么还要char * 类型的返回值?
答:方便赋值给其他变量

6.MFC中CString是类型安全类么?
答:不是,其它数据类型转换到CString可以使用CString的成员函数Format来转换

7.C++中为什么用模板类。
答:(1)可用来创建动态增长和减小的数据结构
(2)它是类型无关的,因此具有很高的可复用性。
(3)它在编译时而不是运行时检查数据类型,保证了类型安全
(4)它是平台无关的,可移植性
(5)可用于基本数据类型

8.CSingleLock是干什么的。
答:同步多个线程对一个数据类的同时访问

9.NEWTEXTMETRIC 是什么。
答:物理字体结构,用来设置字体的高宽大小

10.程序什么时候应该使用线程,什么时候单线程效率高。
答:1.耗时的操作使用线程,提高应用程序响应
2.并行操作时使用线程,如C/S架构的服务器端并发线程响应用户的请求。
3.多CPU系统中,使用线程提高CPU利用率
4.改善程序结构。一个既长又复杂的进程可以考虑分为多个线程,成为几个独立或半独
立的运行部分,这样的程序会利于理解和修改。
其他情况都使用单线程。

11.Windows是内核级线程么。
答:见下一题

12.Linux有内核级线程么。
答:线程通常被定义为一个进程中代码的不同执行路线。从实现方式上划分,线程有两
种类型:“用户级线程”和“内核级线程”。 用户线程指不需要内核支持而在用户程序
中实现的线程,其不依赖于操作系统核心,应用进程利用线程库提供创建、同步、调度
和管理线程的函数来控制用户线程。这种线程甚至在象 DOS 这样的操作系统中也可实现
,但线程的调度需要用户程序完成,这有些类似 Windows 3.x 的协作式多任务。另外一
种则需要内核的参与,由内核完成线程的调度。其依赖于操作系统核心,由内核的内部
需求进行创建和撤销,这两种模型各有其好处和缺点。用户线程不需要额外的内核开支
,并且用户态线程的实现方式可以被定制或修改以适应特殊应用的要求,但是当一个线
程因 I/O 而处于等待状态时,整个进程就会被调度程序切换为等待状态,其他线程得不
到运行的机会;而内核线程则没有各个限制,有利于发挥多处理器的并发优势,但却占
用了更多的系统开支。
Windows NT和OS/2支持内核线程。Linux 支持内核级的多线程

13.C++中什么数据分配在栈或堆中,New分配数据是在近堆还是远堆中?
答:栈: 存放局部变量,函数调用参数,函数返回值,函数返回地址。由系统管理
堆: 程序运行时动态申请,new 和 malloc申请的内存就在堆上

14.使用线程是如何防止出现大的波峰。
答:意思是如何防止同时产生大量的线程,方法是使用线程池,线程池具有可以同时提
高调度效率和限制资源使用的好处,线程池中的线程达到最大数时,其他线程就会排队
等候。

15函数模板与类模板有什么区别?
答:函数模板的实例化是由编译程序在处理函数调用时自动完成的,而类模板的实例化
必须由程序员在程序中显式地指定。

16一般数据库若出现日志满了,会出现什么情况,是否还能使用?
答:只能执行查询等读操作,不能执行更改,备份等写操作,原因是任何写操作都要记
录日志。也就是说基本上处于不能使用的状态。

17 SQL Server是否支持行级锁,有什么好处?
答:支持,设立封锁机制主要是为了对并发操作进行控制,对干扰进行封锁,保证数据
的一致性和准确性,行级封锁确保在用户取得被更新的行到该行进行更新这段时间内不
被其它用户所修改。因而行级锁即可保证数据的一致性又能提高数据操作的迸发性。

18如果数据库满了会出现什么情况,是否还能使用?
答:见16

19 关于内存对齐的问题以及sizof()的输出
答:编译器自动对齐的原因:为了提高程序的性能,数据结构(尤其是栈)应该尽可能
地在自然边界上对齐。原因在于,为了访问未对齐的内存,处理器需要作两次内存访问
;然而,对齐的内存访问仅需要一次访问。

20 int i=10, j=10, k=3; k*=i+j; k最后的值是?
答:60,此题考察优先级,实际写成: k*=(i+j);,赋值运算符优先级最低

21.对数据库的一张表进行操作,同时要对另一张表进行操作,如何实现?
答:将操作多个表的操作放入到事务中进行处理

22.TCP/IP 建立连接的过程?(3-way shake)
答:在TCP/IP协议中,TCP协议提供可靠的连接服务,采用三次握手建立一个连接。
  第一次握手:建立连接时,客户端发送syn包(syn=j)到服务器,并进入SYN_SEND状
态,等待服务器确认;
第二次握手:服务器收到syn包,必须确认客户的SYN(ack=j+1),同时自己也发送一个
SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态;
  第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1)
,此包发送完毕,客户端和服务器进入ESTABLISHED状态,完成三次握手。

23.ICMP是什么协议,处于哪一层?
答:Internet控制报文协议,处于网络层(IP层)

24.触发器怎么工作的?
答:触发器主要是通过事件进行触发而被执行的,当对某一表进行诸如UPDATE、 INSERT
、 DELETE 这些操作时,数据库就会自动执行触发器所定义的SQL 语句,从而确保对数
据的处理必须符合由这些SQL 语句所定义的规则。

25.winsock建立连接的主要实现步骤?
答:服务器端:socker()建立套接字,绑定(bind)并监听(listen),用accept()
等待客户端连接。
客户端:socker()建立套接字,连接(connect)服务器,连接上后使用send()和recv(
),在套接字上写读数据,直至数据交换完毕,closesocket()关闭套接字。
服务器端:accept()发现有客户端连接,建立一个新的套接字,自身重新开始等待连
接。该新产生的套接字使用send()和recv()写读数据,直至数据交换完毕,closesock
et()关闭套接字。

26.动态连接库的两种方式?
答:调用一个DLL中的函数有两种方法:
1.载入时动态链接(load-time dynamic linking),模块非常明确调用某个导出函数
,使得他们就像本地函数一样。这需要链接时链接那些函数所在DLL的导入库,导入库向
系统提供了载入DLL时所需的信息及DLL函数定位。
2.运行时动态链接(run-time dynamic linking),运行时可以通过LoadLibrary或Loa
dLibraryEx函数载入DLL。DLL载入后,模块可以通过调用GetProcAddress获取DLL函数的
出口地址,然后就可以通过返回的函数指针调用DLL函数了。如此即可避免导入库文件了

27.IP组播有那些好处?
答:Internet上产生的许多新的应用,特别是高带宽的多媒体应用,带来了带宽的急剧
消耗和网络拥挤问题。组播是一种允许一个或多个发送者(组播源)发送单一的数据包
到多个接收者(一次的,同时的)的网络技术。组播可以大大的节省网络带宽,因为无
论有多少个目标地址,在整个网络的任何一条链路上只传送单一的数据包。所以说组播
技术的核心就是针对如何节约网络资源的前提下保证服务质量。

----------------------------------------------------------------------------------------------------------

1.static有什么用途?(请至少说明两种)
    1)在函数体,一个被声明为静态的变量在这一函数被调用过程中维持其值不变。
    2) 在模块内(但在函数体外),一个被声明为静态的变量可以被模块内所用函数访问,但不能被模块外其它函数访问。它是一个本地的全局变量。
    3) 在模块内,一个被声明为静态的函数只可被这一模块内的其它函数调用。那就是,这个函数被限制在声明它的模块的本地范围内使用

2.引用与指针有什么区别?
    1) 引用必须被初始化,指针不必。
    2) 引用初始化以后不能被改变,指针可以改变所指的对象。
    3) 不存在指向空值的引用,但是存在指向空值的指针。

3.描述实时系统的基本特性
       在特定时间内完成特定的任务,实时性与可靠性。

4.全局变量和局部变量在内存中是否有区别?如果有,是什么区别?
      全局变量储存在静态数据库,局部变量在堆栈。

5.什么是平衡二叉树?
      左右子树都是平衡二叉树 且左右子树的深度差值的绝对值不大于1。

6.堆栈溢出一般是由什么原因导致的?
      没有回收垃圾资源。

7.什么函数不能声明为虚函数?
      constructor函数不能声明为虚函数。

8.冒泡排序算法的时间复杂度是什么?
      时间复杂度是O(n^2)。

9.写出float x 与“零值”比较的if语句。
      if(x>0.000001&&x<-0.000001)

10.Internet采用哪种网络协议?该协议的主要层次结构?
      Tcp/Ip协议
      主要层次结构为: 应用层/传输层/网络层/数据链路层/物理层。

11.Internet物理地址和IP地址转换采用什么协议?
      ARP (Address Resolution Protocol)(地址解析協議)

12.IP地址的编码分为哪俩部分?
     IP地址由两部分组成,网络号和主机号。不过是要和“子网掩码”按位与上之后才能区分哪些是网络位哪些是主机位。

13.用户输入M,N值,从1至N开始顺序循环数数,每数到M输出该数值,直至全部输出。写出C程序。
     循环链表,用取余操作做
14.不能做switch()的参数类型是:
     switch的参数不能为实型。

----------------------------------------------------------------------------------------------------------

1、局部变量能否和全局变量重名?
     答:能,局部会屏蔽全局。要用全局变量,需要使用"::"
局部变量可以与全局变量同名,在函数内引用这个变量时,会用到同名的局部变量,而不会用到全局变量。对于有些编译器而言,在同一个函数内可以定义多个同名的局部变量,比如在两个循环体内都定义一个同名的局部变量,而那个局部变量的作用域就在那个循环体内。

2、如何引用一个已经定义过的全局变量?
     答:extern
     可以用引用头文件的方式,也可以用extern关键字,如果用引用头文件方式来引用某个在头文件中声明的全局变理,假定你将那个变写错了,那么在编译期间会报错,如果你用extern方式引用时,假定你犯了同样的错误,那么在编译期间不会报错,而在连接期间报错。

3、全局变量可不可以定义在可被多个.C文件包含的头文件中?为什么?
    答:可以,在不同的C文件中以static形式来声明同名全局变量。
    可以在不同的C文件中声明同名的全局变量,前提是其中只能有一个C文件中对此变量赋初值,此时连接不会出错。

 

----------------------------------------------------------------------------------------------------------

1、static全局变量与普通的全局变量有什么区别?static局部变量和普通局部变量有什么区别?static函数与普通函数有什么区别?
    答:全局变量(外部变量)的说明之前再冠以static 就构成了静态的全局变量。全局变量本身就是静态存储方式, 静态全局变量当然也是静态存储方式。 这两者在存储方式上并无不同。这两者的区别虽在于非静态全局变量的作用域是整个源程序, 当一个源程序由多个源文件组成时,非静态的全局变量在各个源文件中都是有效的。 而静态全局变量则限制了其作用域, 即只在定义该变量的源文件内有效, 在同一源程序的其它源文件中不能使用它。由于静态全局变量的作用域局限于一个源文件内,只能为该源文件内的函数公用, 因此可以避免在其它源文件中引起错误。
    从以上分析可以看出, 把局部变量改变为静态变量后是改变了它的存储方式即改变了它的生存期。把全局变量改变为静态变量后是改变了它的作用域, 限制了它的使用范围。
    static函数与普通函数作用域不同。仅在本文件。只在当前源文件中使用的函数应该说明为内部函数(static),内部函数应该在当前源文件中说明和定义。对于可在当前源文件以外使用的函数,应该在一个头文件中说明,要使用这些函数的源文件要包含这个头文件
    static全局变量与普通的全局变量有什么区别:static全局变量只初使化一次,防止在其他文件单元中被引用;
    static局部变量和普通局部变量有什么区别:static局部变量只被初始化一次,下一次依据上一次结果值;
    static函数与普通函数有什么区别:static函数在内存中只有一份,普通函数在每个被调用中维持一份拷贝

2、程序的局部变量存在于(堆栈)中,全局变量存在于(静态区 )中,动态申请数据存在于( 堆)中。

3、设有以下说明和定义:
typedef union {long i; int k[5]; char c;} DATE;
struct data { int cat; DATE cow; double dog;} too;
DATE max;
则语句 printf("%d",sizeof(struct date)+sizeof(max));的执行结果是:___52____
    答:DATE是一个union, 变量公用空间. 里面最大的变量类型是int[5], 占用20个字节. 所以它的大小是20
data是一个struct, 每个变量分开占用空间. 依次为int4 + DATE20 + double8 = 32.
所以结果是 20 + 32 = 52.
当然...在某些16位编辑器下, int可能是2字节,那么结果是 int2 + DATE10 + double8 = 20

4、队列和栈有什么区别?
    队列先进先出,栈后进先出

5、写出下列代码的输出内容
#include "stdio.h"
int inc(int a)
{
return(++a);
}
int multi(int*a,int*b,int*c)
{
return(*c=*a**b);
}
typedef int(FUNC1)(int in);
typedef int(FUNC2) (int*,int*,int*);

void show(FUNC2 fun,int arg1, int*arg2)
{
INCp=&inc;
int temp =p(arg1);
fun(&temp,&arg1, arg2);
printf("%dn",*arg2);
}

main()
{
int a;
show(multi,10,&a);
return 0;
}
答:110
7、请找出下面代码中的所以错误
说明:以下代码是把一个字符串倒序,如“abcd”倒序后变为“dcba”

1、#i nclude"string.h"
2、main()
3、{
4、 char*src="hello,world";
5、 char* dest=NULL;
6、 int len=strlen(src);
7、 dest=(char*)malloc(len);
8、 char* d=dest;
9、 char* s=src[len];
10、 while(len--!=0)
11、 d++=s--;
12、 printf("%s",dest);
13、 return 0;
14、}
答:
方法1:
int main(){
char* src = "hello,world";
int len = strlen(src);
char* dest = (char*)malloc(len+1);//要为0分配一个空间
char* d = dest;
char* s = &src[len-1];//指向最后一个字符
while( len-- != 0 )
*d++=*s--;
*d = 0;//尾部要加0
printf("%sn",dest);
free(dest);// 使用完,应当释放空间,以免造成内存汇泄露
return 0;
}
方法2:

#include "string.h"
#include "stdio.h"
main()
{
char str[]="hello,world";
int len=strlen(str);
char t;
for(int i=0; i{
t=str[i];
str[i]=str[len-i-1]; str[len-i-1]=t;
}
printf("%s",str);
return 0;
}

硬件工程师面试试题

分类:默认栏目

模拟电路
1、 基尔霍夫定理的内容是什么?
基尔霍夫定律包括电流定律和电压定律
电流定律:在集总电路中,任何时刻,对任一节点,所有流出节点的支路电流的代数和恒等于零。
电压定律:在集总电路中,任何时刻,沿任一回路,所有支路电压的代数和恒等于零。
2、 描述反馈电路的概念,列举他们的应用。
反馈,就是在电子系统中,把输出回路中的电量输入到输入回路中去。
反馈的类型有:电压串联负反馈、电流串联负反馈、电压并联负反馈、电流并联负反馈。
负反馈的优点:降低放大器的增益灵敏度,改变输入电阻和输出电阻,改善放大器的线性和非线性失真,有效地扩展放大器的通频带,自动调节作用。
电压负反馈的特点:电路的输出电压趋向于维持恒定。
电流负反馈的特点:电路的输出电流趋向于维持恒定。
3、 有源滤波器和无源滤波器的区别
无源滤波器:这种电路主要有无源元件R、L和C组成
有源滤波器:集成运放和R、C组成,具有不用电感、体积小、重量轻等优点。
集成运放的开环电压增益和输入阻抗均很高,输出电阻小,构成有源滤波电路后还具有一定的电压放大和缓冲作用。但集成运放带宽有限,所以目前的有源滤波电路的工作频率难以做得很高。
数字电路
1、 同步电路和异步电路的区别是什么?
同步电路:存储电路中所有触发器的时钟输入端都接同一个时钟脉冲源,因而所有触发器的状态的变化都与所加的时钟脉冲信号同步。
异步电路:电路没有统一的时钟,有些触发器的时钟输入端与时钟脉冲源相连,这有这些触发器的状态变化与时钟脉冲同步,而其他的触发器的状态变化不与时钟脉冲同步。
2、 什么是" 线与" 逻辑,要实现它,在硬件特性上有什么具体要求?
将两个门电路的输出端并联以实现与逻辑的功能成为线与。
在硬件上,要用OC门来实现,同时在输出端口加一个上拉电阻。
由于不用OC门可能使灌电流过大,而烧坏逻辑门。
3 、解释setup 和hold time violation ,画图说明,并说明解决办法。(威盛VIA2003.11.06 上海笔试试题)
Setup/hold time是测试芯片对输入信号和时钟信号之间的时间要求。建立时间是指触发器的时钟信号上升沿到来以前,数据稳定不变的时间。输入信号应提前时钟上升沿(如上升沿有效)T时间到达芯片,这个T就是建立时间-Setup time.如不满足setup time,这个数据就不能被这一时钟打入触发器,只有在下一个时钟上升沿,数据才能被打入触发器。
保持时间是指触发器的时钟信号上升沿到来以后,数据稳定不变的时间。如果hold time不够,数据同样不能被打入触发器。
建立时间(Setup Time)和保持时间(Hold time)。建立时间是指在时钟边沿前,数据信号需要保持不变的时间。保持时间是指时钟跳变边沿后数据信号需要保持不变的时间。如果数据信号在时钟沿触发前后持续的时间均超过建立和保持时间,那么超过量就分别被称为建立时间裕量和保持时间裕量。
4 、什么是竞争与冒险现象?怎样判断?如何消除?(汉王笔试)
在组合逻辑中,由于门的输入信号通路中经过了不同的延时,导致到达该门的时间不一致叫竞争。
产生毛刺叫冒险。如果布尔式中有相反的信号则可能产生竞争和冒险现象。
解决方法:一是添加布尔式的消去项,二是在芯片外部加电容。
5、 名词:SRAM 、SSRAM 、SDRAM
SRAM:静态RAM
DRAM:动态RAM
SSRAM:Synchronous Static Random Access Memory同步静态随机访问存储器。它的一种类型的SRAM。SSRAM的所有访问都在时钟的上升/下降沿启动。地址、数据输入和其它控制信号均于时钟信号相关。这一点与异步SRAM不同,异步SRAM的访问独立于时钟,数据输入和输出都由地址的变化控制。
SDRAM:Synchronous DRAM同步动态随机存储器
6 、FPGA 和ASIC 的概念,他们的区别。(未知)
答案:FPGA是可编程ASIC。   
ASIC:专用集成电路,它是面向专门用途的电路,专门为一个用户设计和制造的。根据一个用户的特定要求,能以低研制成本,短、交货周期供货的全定制,半定制集成电路。与 门阵列等其它 ASIC(Application Specific IC)相比,它们又具有设计开发周期短、设计制造成本低、开发工具先进、标准产品无需测试、质量稳定以及可实时在线检验等优点。
7 、什么叫做OTP 片、掩膜片,两者的区别何在?
OTP means one time program,一次性编程
MTP means multi time program,多次性编程
OTP(One Time Program)是MCU的一种存储器类型
MCU按其存储器类型可分为MASK(掩模)ROM、OTP(一次性可编程)ROM、FLASHROM等类型。
MASKROM MCU 价格便宜,但程序在出厂时已经固化,适合程序固定不变的应用场合;
FALSHROM的MCU程序可以反复擦写,灵活性很强,但价格较高,适合对价格不敏感的应用场合或做开发用途;
OTP ROM的MCU价格介于前两者之间,同时又拥有一次性可编程能力,适合既要求一定灵活性,又要求低成本的应用场合,尤其是功能不断翻新、需要迅速量产的电子产品。
8 、单片机上电后没有运转,首先要检查什么?
首先应该确认电源电压是否正常。用电压表测量接地引脚跟电源引脚之间的电压,看是否是电源电压,例如常用的5V。
接下来就是检查复位引脚电压是否正常。分别测量按下复位按钮和放开复位按钮的电压值,看是否正确。
然后再检查晶振是否起振了,一般用示波器来看晶振引脚的波形,注意应该使用示波器探头的“X10”档。另一个办法是测量复位状态下的IO口电平,按住复位键不放,然后测量IO口(没接外部上拉的P0口除外)的电压,看是否是高电平,如果不是高电平,则多半是因为晶振没有起振。
另外还要注意的地方是,如果使用片内ROM的话(大部分情况下如此,现在已经很少有用外部扩ROM的了),一定要将EA引脚拉高,否则会出现程序乱跑的情况。有时用仿真器可以,而烧入片子不行,往往是因为EA引脚没拉高的缘故(当然,晶振没起振也是原因只一)。经过上面几点的检查,一般即可排除故障了 。如果系统不稳定的话,有时是因为电源滤波不好导致的。在单片机的电源引脚跟地引脚之间接上一个0.1uF的电容会有所改善 。如果电源没有滤波电容的话,则需要再接一个更大滤波电容,例如220uF的。遇到系统不稳定时,就可以并上电容试试(越靠近芯片越好)。

VC调试入门(转)

分类:默认栏目

 概述
调试是一个程序员最基本的技能,其重要性甚至超过学习一门语言。不会调试的程序员就意味着他即使会一门语言,却不能编制出任何好的软件。
这里我简要的根据自己的经验列出调试中比较常用的技巧,希望对大家有用。
本文约定,在选择菜单时,通过/表示分级菜单,例如File/Open表示顶级菜单File的子菜单Open。
 
 设置
为了调试一个程序,首先必须使程序中包含调试信息。一般情况下,一个从AppWizard创建的工程中包含的Debug Configuration自动包含调试信息,但是是不是Debug版本并不是程序包含调试信息的决定因素,程序设计者可以在任意的Configuration中增加调试信息,包括Release版本。
为了增加调试信息,可以按照下述步骤进行: 

  • 打开Project settings对话框(可以通过快捷键ALT+F7打开,也可以通过IDE菜单Project/Settings打开) 
  • 选择C/C++页,Category中选择general ,则出现一个Debug Info下拉列表框,可供选择的调试信息 方式包括: 
      
    命令行Project settings说明
    None没有调试信息
    /ZdLine Numbers Only目标文件或者可执行文件中只包含全局和导出符号以及代码行信息,不包含符号调试信息
    /Z7C 7.0- Compatible目标文件或者可执行文件中包含行号和所有符号调试信息,包括变量名及类型,函数及原型等
    /ZiProgram Database创建一个程序库(PDB),包括类型信息和符号调试信息。
    /ZIProgram Database for Edit and Continue除了前面/Zi的功能外,这个选项允许对代码进行调试过程中的修改和继续执行。这个选项同时使#pragma设置的优化功能无效

  • 选择Link页,选中复选框"Generate Debug Info",这个选项将使连接器把调试信息写进可执行文件和DLL 
  • 如果C/C++页中设置了Program Database以上的选项,则Link incrementally可以选择。选中这个选项,将使程序可以在上一次编译的基础上被编译(即增量编译),而不必每次都从头开始编译。 

 断点
断点是调试器设置的一个代码位置。当程序运行到断点时,程序中断执行,回到调试器。断点是 最常用的技巧。调试时,只有设置了断点并使程序回到调试器,才能对程序进行在线调试。

设置断点:可以通过下述方法设置一个断点。首先把光标移动到需要设置断点的代码行上,然后 

  • 按F9快捷键 
  • 弹出Breakpoints对话框,方法是按快捷键CTRL+B或ALT+F9,或者通过菜单Edit/Breakpoints打开。打开后点击Break at编辑框的右侧的箭头,选择 合适的位置信息。一般情况下,直接选择line xxx就足够了,如果想设置不是当前位置的断点,可以选择Advanced,然后填写函数、行号和可执行文件信息。 

去掉断点:把光标移动到给定断点所在的行,再次按F9就可以取消断点。同前面所述,打开Breakpoints对话框后,也可以按照界面提示去掉断点。

条件断点:可以为断点设置一个条件,这样的断点称为条件断点。对于新加的断点,可以单击Conditions按钮,为断点设置一个表达式。当这个表达式发生改变时,程序就 被中断。底下设置包括“观察数组或者结构的元素个数”,似乎可以设置一个指针所指向的内存区的大小,但是我设置一个比较的值但是改动 范围之外的内存区似乎也导致断点起效。最后一个设置可以让程序先执行多少次然后才到达断点。

数据断点:数据断点只能在Breakpoints对话框中设置。选择“Data”页,就显示了设置数据断点的对话框。在编辑框中输入一个表达式,当这个 表达式的值发生变化时,数据断点就到达。一般情况下,这个表达式应该由运算符和全局变量构成,例如:在编辑框中输入 g_bFlag这个全局变量的名字,那么当程序中有g_bFlag= !g_bFlag时,程序就将停在这个语句处。

消息断点:VC也支持对Windows消息进行截获。他有两种方式进行截获:窗口消息处理函数和特定消息中断。
在Breakpoints对话框中选择Messages页,就可以设置消息断点。如果在上面那个对话框中写入消息处理函数的名字,那么 每次消息被这个函数处理,断点就到达(我觉得如果采用普通断点在这个函数中截获,效果应该一样)。如果在底下的下拉 列表框选择一个消息,则每次这种消息到达,程序就中断。

 值
Watch
VC支持查看变量、表达式和内存的值。所有这些观察都必须是在断点中断的情况下进行。
观看变量的值最简单,当断点到达时,把光标移动到这个变量上,停留一会就可以看到变量的值。
VC提供一种被成为Watch的机制来观看变量和表达式的值。在断点状态下,在变量上单击右键,选择Quick Watch, 就弹出一个对话框,显示这个变量的值。
单击Debug工具条上的Watch按钮,就出现一个Watch视图(Watch1,Watch2,Watch3,Watch4),在该视图中输入变量或者表达式,就可以观察 变量或者表达式的值。注意:这个表达式不能有副作用,例如++运算符绝对禁止用于这个表达式中,因为这个运算符将修改变量的值,导致 软件的逻辑被破坏。

Memory
由于指针指向的数组,Watch只能显示第一个元素的值。为了显示数组的后续内容,或者要显示一片内存的内容,可以使用memory功能。在 Debug工具条上点memory按钮,就弹出一个对话框,在其中输入地址,就可以显示该地址指向的内存的内容。

Varibles

Debug工具条上的Varibles按钮弹出一个框,显示所有当前执行上下文中可见的变量的值。特别是当前指令涉及的变量,以红色显示。

寄存器
Debug工具条上的Reigsters按钮弹出一个框,显示当前的所有寄存器的值。

 进程控制
VC允许被中断的程序继续运行、单步运行和运行到指定光标处,分别对应快捷键F5、F10/F11和CTRL+F10。各个快捷键功能如下: 
  

快捷键说明
F5继续运行
F10单步,如果涉及到子函数,不进入子函数内部
F11单步,如果涉及到子函数,进入子函数内部
CTRL+F10运行到当前光标处。

 Call Stack
调用堆栈反映了当前断点处函数是被那些函数按照什么顺序调用的。单击Debug工具条上的Call stack就显示Call Stack对话框。在CallStack对话框中显示了一个调用系列,最上面的是当前函数,往下依次是调用函数的上级函数。单击这些函数名可以跳到对应的函数中去。

 其他调试手段
系统提供一系列特殊的函数或者宏来处理Debug版本相关的信息,如下: 

宏名/函数名说明
TRACE使用方法和printf完全一致,他在output框中输出调试信息
ASSERT它接收一个表达式,如果这个表达式为TRUE,则无动作,否则中断当前程序执行。对于系统中出现这个宏 导致的中断,应该认为你的函数调用未能满足系统的调用此函数的前提条件。例如,对于一个还没有创建的窗口调用SetWindowText等。
VERIFY和ASSERT功能类似,所不同的是,在Release版本中,ASSERT不计算输入的表达式的值,而VERIFY计算表达式的值。

 关注
一个好的程序员不应该把所有的判断交给编译器和调试器,应该在程序中自己加以程序保护和错误定位,具体措施包括: 

  • 对于所有有返回值的函数,都应该检查返回值,除非你确信这个函数调用绝对不会出错,或者不关心它是否出错。 
  • 一些函数返回错误,需要用其他函数获得错误的具体信息。例如accept返回INVALID_SOCKET表示accept失败,为了查明 具体的失败原因,应该立刻用WSAGetLastError获得错误码,并针对性的解决问题。 
  • 有些函数通过异常机制抛出错误,应该用TRY-CATCH语句来检查错误 
  • 程序员对于能处理的错误,应该自己在底层处理,对于不能处理的,应该报告给用户让他们决定怎么处理。如果程序出了异常, 却不对返回值和其他机制返回的错误信息进行判断,只能是加大了找错误的难度。 

另外:VC中要编制程序不应该一开始就写cpp/h文件,而应该首先创建一个合适的工程。因为只有这样,VC才能选择合适的编译、连接 选项。对于加入到工程中的cpp文件,应该检查是否在第一行显式的包含stdafx.h头文件,这是Microsoft Visual Studio为了加快编译 速度而设置的预编译头文件。在这个#include "stdafx.h"行前面的所有代码将被忽略,所以其他头文件应该在这一行后面被包含。
对于.c文件,由于不能包含stdafx.h,因此可以通过Project settings把它的预编译头设置为“不使用”,方法是: 

  • 弹出Project settings对话框 
  • 选择C/C++ 
  • Category选择Precompilation Header 
  • 选择不使用预编译头。 

c/c 笔试题

分类:默认栏目

1. 以下三条输出语句分别输出什么?[C易]
char str1[]       = "abc";
char str2[]       = "abc";
const char str3[] = "abc";
const char str4[] = "abc";
const char* str5  = "abc";
const char* str6  = "abc";
cout << boolalpha << ( str1==str2 ) << endl; // 输出什么?
cout << boolalpha << ( str3==str4 ) << endl; // 输出什么?
cout << boolalpha << ( str5==str6 ) << endl; // 输出什么?

答:分别输出false,false,true。str1和str2都是字符数组,每个都有其自己的存储区,它们的值则是各存储区首地址,不等;str3和str4同上,只是按const语义,它们所指向的数据区不能修改。str5和str6并非数组而是字符指针,并不分配存储区,其后的“abc”以常量形式存于静态数据区,而它们自己仅是指向该区首地址的指针,相等

内联函数

分类:默认栏目

1.内联函数的定义:inline 函数类型 函数名(......);

2.内联函数通过编译器控制来实现。编译系统在遇到内联函数时会将其实现部分的所有语句直接在调用程序中展开,因而减少了与函数调用和参数传递有关的系统开销。但由于内联函数增加了函数调用的空间开销,因此通常只在实现部分语句较少或系统相应速度要求较高时才使用内联函数;

3.内联函数中不允许使用循环语句和开关语句;

4.内联函数的定义必须出现在它第一次被调用之前;

5.在类内部定义的函数都是内联的

6.如果函数体过大,一般的编译器会放弃内联方式,而采用普通方式进行调用

友元函数

分类:

一、友元函数的定义

一个类的友元函数是在该类中声明的一个函数,它不是类的成员函数,但允许访问该类的所有成员(私有成员、保护成员、公有成员)。

二、友元函数的声明

class 类名

{

......

public:

    friend 函数类型 函数名称();//声明友元

......

}

三、友元函数的特点

1.友元可以是一般的函数(友元函数),也可以是另一个类的成员函数(友元成员),还可是整个一个类(友元类);

2.友元函数须在私有成员被它访问的类中声明,而函数体则在类外声明

3.友元函数不是类的成员函数,(类的朋友,具有信任关系)而是独立于任何类的一般外界函数;

4.C++中使用友元是为了提高程序的运行效率。但为了保证数据的完整性和数据的封装性,应尽量不使用或少使用友元函数

  • 0
    点赞
  • 1
    评论
  • 2
    收藏
  • 一键三连
    一键三连
  • 扫一扫,分享海报

©️2021 CSDN 皮肤主题: 大白 设计师:CSDN官方博客 返回首页
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值