C++笔试题大全----下

一、输入一个n ,然后在屏幕上打印出NxN的矩阵!

例如,输入一个3,则

1 23

8 94

7 65

输入一个4,则

1 2 3 4

1213 14 5

1116 15 6

10 98 7

参考答案:

 

#include<stdio.h>

#include<conio.h>

#define N 10

 

void printCube(int a[][N],int n);

 

void main()

{

   int a[N][N],n;

   printf("input n:\n");

   scanf("%d",&n);

   printCube(&a[0],n);

   getch();

}

 

void printCube(int a[][N],int n)

{

   int i,j,round=1;

   int m=1;

   for(i=0;i<n;i++)

a[0]=m++;

   for(i=n-1;i>=n/2;i--)

   {

for(j=round;j<=i;j++)

   a[j]=m++;

for(j=i;j>=round;j--)

   a[j-1]=m++;

for(j=i;j>round;j--)

   a[j-1][round-1]=m++;

for(j=round;j<i;j++)

   a[round][j]=m++;

round++;

   }

   for(i=0;i<n;i++){

for(j=0;j<n;j++)

printf("%3d",a[j]);

printf("\n");

   }

}

 

二、朗讯面试题 :

Thereare two int variables: a and b, don’t use “if”, “? :”, “switch” or otherjudgement statements, find out the biggest one of the two numbers.

参考答案:

方案一

int max = ((a+b)+abs(a-b)) / 2

 

方案二

int c = a -b;

char *strs[2] = {"a大","b大"};

c = unsigned(c) >> (sizeof(int) * 8 - 1);

 

三、朗讯面试题 :

如何打印出当前源文件的文件名以及源文件的当前行号?

参考答案:

通常使用的就是__FILE__, __LINE__,在调试函数中利用“%s","%ld",打印就好了。

 

四、朗讯面试题 :

main主函数执行完毕后,是否可能会再执行一段代码,给出说明?

参考答案:

crt会执行另一些代码,进行处理工作。

如果你需要加入一段在main退出后执行的代码,可以使用atexit()函数,注册一个函数。

语法:

#include <stdlib.h>

int atexit(void (*function")(void));

#include <stdlib.h>

#include <stdio.h>

 

void fn1( void ), fn2( void ), fn3( void ), fn4( void );

 

int main( void )

{

   atexit( fn1 );

   atexit( fn2 );

   atexit( fn3 );

   atexit( fn4 );

   printf( "This is executed first.\n" );

}

 

void fn1()

{

   printf( "next.\n" );

}

 

void fn2()

{

   printf( "executed " );

}

 

void fn3()

{

   printf( "is " );

}

 

void fn4()

{

   printf( "This " );

}

 

五、朗讯面试题 :

如何判断一段程序是由C编译程序还是由C++编译程序编译的?

参考答案:

c++编译时定义了 __cplusplus

c编译时定义了 _STDC_

 

六、下面这道面试题怎么做(指针)?

#include<stdio.h>

main(){

int c[3][3]={1,2,3,4,5,6,7,8,9};

for(int i=0;i<3;i++)

for(int j=0;j<3;j++)

printf("%ld\n",&c[j]);

printf("-------------------------\n");

printf("%ld\n",(c+1));

printf("%ld\n",(*c+1));

printf("%ld\n",&c[0][0]);

printf("%ld\n",**c);

printf("%ld\n",*c[0]);

if(int(c)==int(*c))

printf("equl");

}

为什么c,*c的值相等,(c+1),(*c+1)的值不等

c,*c,**c,代表什么意思?

 

参考答案:

c是第一个元素的地址,*c是第一行元素的首地址,其实第一行元素的地址就是第一个元素的地址,这容易理解。**c是提领第一个元素。

为什么c,*c的值相等?

int c因为直接用c表示数组c[0][0]

printf("%ld\n",*c[0]);语句已将指针移到数组头。

int(*c)表示c0的值为1,所以相等。

数组c的存放空间示意如下:(机器中是行优先存放的)

c[0][0] c[0][1] c[0][2]

c[1][0] c[1][1] c[1][2]

c[2][0] c[2][1] c[2][2]

 

c是一个二维数组名,实际上它是一个指针常量,不能进行自加、自减运算,即:c++、c--、++c、--c

都是不允许的;

c: 数组名;是一个二维指针,它的值就是数组的首地址,也即第一行元素的首地址(等于 *c),也

     等于第一行第一个元素的地址( & c[0][0]);可以说成是二维数组的行指针。

*c: 第一行元素的首地址;是一个一维指针,可以说成是二维数组的列指针。

**c:二维数组中的第一个元素的值;即:c[0][0]

所以:

     c 和 *c的值是相等的,但他们两者不能相互赋值,(类型不同);

     (c + 1) :c是行指针,(c + 1)是在c的基础上加上二维数组一行的地址长度,即从&c[0][0]

     变到了&c[1][0];

    (*c + 1):*c是列指针,(*c + 1)是在*c的基础上加上二数组一个元素的所占的长度,即从

     &c[0][0]变到了&c[0][1]

     从而(c + 1)和(*c + 1)的值就不相等了

 

七、定义 int **a[3][4], 则变量占有的内存空间为:_____

参考答案:

int **p; /*16位下sizeof(p)=2, 32位下sizeof(p)=4*/

总共 3*4*sizeof(p)

 

八、编写一个函数,要求输入年月日时分秒,输出该年月日时分秒的下一秒。如输入2004年12月31日23时59分59秒,则输出2005年1月1日0时0分0秒。

参考答案:

判断年份是否是闰年,月份的大小月,

月(12进制)、日(与闰年、大小月有关)、时(24进制)、分(60进制)、妙(60进制)

 

 

经典10道c/c++语言经典笔试题(含全部所有参考答案)

1. 下面这段代码的输出是多少(在32位机上).

char *p;

char *q[20];

char *m[20][20];

 

int(*n)[10];

structMyStruct

{

chardda;

doubledda1;

inttype ;

};

MyStructk;

printf("%d%d %d %d %d",sizeof(p),sizeof(q),sizeof(m),sizeof(n),sizeof(k));

 

2.

(1)

chara[2][2][3]={{{1,6,3},{5,4,15}},{{3,5,33},{23,12,7}}};

for(inti=0;i<12;i++)

printf("%d",_______);

在空格处填上合适的语句,顺序打印出a中的数字

(2)

char**p, a[16][8];

问:p=a是否会导致程序在以后出现问题?为什么?

 

4.strcpy函数和memcpy函数有什么区别?它们各自使用时应该注意什么问题?

 

5.(1)写一个函数将一个链表逆序.

(2)一个单链表,不知道长度,写一个函数快速找到中间节点的位置.

(3)写一个函数找出一个单向链表的倒数第n个节点的指针.(把能想到的最好算法写出).

 

6.用递归算法判断数组a[N]是否为一个递增数组。

 

7.有一个文件(名为a.txt)如下,每行有4项,第一项是他们的名次,写一个c程序,将五个人的名字打印出来.并按名次排序后将5行数据仍然保存到a.txt中.使文件按名次排列每行.

2,07010188,0711,李镇豪,

1,07010154,0421,陈亦良,

3,07010194,0312,凌瑞松,

4,07010209,0351,罗安祥,

5,07010237,0961,黄世传,

 

8.(1)写一个函数,判断一个unsigned char 字符有几位是1.

(2)写一个函数判断计算机的字节存储顺序是升序(little-endian)还是降序(big-endian).

 

9.微软的笔试题.

Implementa string class in C++ with basic functionality like comparison, concatenation,input and output. Please also provide some test cases and using scenarios(sample code of using this class).

Pleasedo not use MFC, STL and other libraries in your implementation.

 

10.有个数组a[100]存放了100个数,这100个数取自1-99,且只有两个相同的数,剩下的98个数不同,写一个搜索算法找出相同的那个数的值.(注意空间效率时间效率尽可能要低).

 

1.

4

80

1600

4 //定义的是一个指向数组的指针

24//直接对齐

 

2.

(1)

*(&a[0][0][0]+i)

(2)

编译能通过,就算强制转换也会有问题,a和p所采取的内存布局和寻址方式不同,a的内存假定是连续的,对于a[i][j]可等价于*(&a[0][0]+16*i+j),而char**p不假定使用的是连续的内存,p[i][j]=*(p[i]+j);

 

3.

非递归方式:

char*reverse(char *str)

{

intlen = strlen(str);

chartemp;

for(inti=0; i<len/2; i++)

{

temp = *(str+i);

*(str+i) = *(str+len-1-i);

*(str+len-1-i) = temp;

}

return str;

}

 

递归方式:

char *reverse(char *str)

{

ASSERT(str!=NULL);

char tempstr[1024];

char tempchar ;

memset(tempstr,0,1024);

strcpy(tempstr,str);

int i = strlen(tempstr);

switch(i)

{

case1:

break;

case2:

tempchar = str[0];

str[0] = str[1];

str[1] = tempchar;

break;

default:

tempchar=str[0] ;

reverse(str+1);

strcpy(str , str+1);

str[strlen(str)] = tempchar;

break;

}

return str;

}

char *reverse(char *str)

{

assert(str!=NULL);

 

staticchar result[256] = "";

if(*str != '\0')

{

strncat(result,str, 1);

str++;

return(reverse_recursive(str));

}

else

returnresult;

}

 

完整程序:

#include<stdio.h>

#include<string.h>

#include<malloc.h>

#include<assert.h>

 

char*reverse(char *str)

{

assert(str!=NULL);

 

char*result;

 

inti, l = strlen(str);

result= (char *)malloc((l+1)*sizeof(char));

 

for (i=0; i<l; i++)

{

result[i] = str[l-1-i];

}

result[i]= '\0';

 

char*reverse_recursive(char *str)

{

assert(str!=NULL);

 

staticchar result[256] = "";

if(*str != '\0')

{

strncat(result,str, 1);

str++;

return(reverse_recursive(str));

}

else

returnresult;

}

 

intmain()

{

char*rs, *sr = "abcde";

printf("%s\n",sr);

rs =reverse(sr);

printf("%s\n",rs);

free(rs);

rs =reverse_recursive(sr);

printf("%s\n",rs);

 

 

4.

strcpy是复制字符串, 只能操作 char *

memcpy是内存赋值, 可以复制任何数据。

1)参数类型不同

2)操作方式不同, strcpy 根据参数字符串自动寻找终结位置, memcpy 由参数指定复制长度

 

 

5.

(1)

Node* ReverseList(Node *head) //链表逆序

{

if (head == NULL || head->next == NULL )

returnhead;

 

Node*p1 = head ;

Node*p2 = p1->next ;

Node*p3 = p2->next ;

p1->next= NULL ;

 

while( p3 != NULL )

{

p2->next= p1 ;

p1 =p2 ;

p2 =p3 ;

p3 =p3->next ;

}

p2->next= p1;

head= p2 ;

returnhead ;

}

 

 

//2)设置2个指针,一个走2步时,另一个走1步。那么一个走到头时,另一个走到中间。

//3)同2),设置2个指针,一个走了n步以后,另一个才开始走。

(2)

node *(List &l)

{

node *p1 = l;

node*p2 = p1;

while(p2 )

{

p2 =p2->next;

if(p2)

{

p2 =p2->next;

p1=p1->next;

}

}

returnp1;

}

 

(3)

node *(List &l,int n)

{

node*next = l;

node*pre = NULL;

while(n-- > 0 && (next != NULL)

{

next= next->next;

}

if(next!= NULL)

pre= l;

while(next!=NULL)

{

next= next->next;

pre= pre->next;

}

returnpre;

}

 

 

6.用递归算法判断数组a[N]是否为一个递增数组。

usingnamespace std;

boolIsAsc(int*begin,int *end)

{

if(begin== end) return true;

if(*begin>*(begin+1))return false;

returnIsAsc(++begin,end);

}

或:

boolIsIncrease(int *a,int N)

{

returnN<=1 || a[0]<=a[1] && IsIncrease(a+1,N-1) ;

}

 

 

7.

#include<stdio.h>

#include<stdlib.h>

 

structDataLine

{

intno;

chardata1[20];

chardata2[20];

charname[20];

};

 

intmain()

{

DataLinedl[10];

chardata[1024] = "\0";

chartemp[20] = "\0";

char*pch,*ptmp;

 

FILE*fd;

inti = 0;

 

if((fd = fopen("a.txt","r")) == NULL)

{

printf("a.txtcan not open!\n");

exit -1;

}

 

for(int i = 0; i < 5; i++)

{

fseek(fd, 0, SEEK_SET );

while(fgets(data,1024, fd))

{

pch= strchr(data,",");

ptmp= data;

while(pch!=NULL)

{

memset(temp,0x00,sizeof(temp));

//getthe data

strncpy(temp,ptmp,pch- ptmp);

 

//copythe date to dl according the length of temp

 

if((strlen(temp) == 1) && ((i + 1) == atoi[temp]))

{

switch(strlen(temp))

{

case1:

dl[i].no= atoi[temp];

break;

case8:

strncpy(dl[i].data1,temp,8);

break;

case4:

strncpy(dl[i].data2,temp,4);

break;

default:

strcpy(dl[i].name,temp);

break;

}

}

 

ptmp= pch;

pch= strchr(pch+1,',');

}

}

}

 

fclose(fd);

 

if((fd = fopen("a.txt","w")) == NULL)

{

printf("a.txtcan not open!\n");

exit-1;

}

 

for(i= 0; j < 5; i++)

{

printf("%d\t%s\n",i+1,dl[i].name);

fprintf(fd,"%d,%s,%s,%s,\n",dl[i].no,dl[i].data1,dl[i].data2,dl[i].name);

}

 

fclose(fd);

 

return0;

}

 

8.(1)写一个函数,判断一个unsigned char 字符有几位是1.

intGetBit(unsigned char val)

{

intcount=0;

while(val)

{

++count;

val&= (val-1);

}

returncount;

}

 

(2)写一个函数判断计算机的字节存储顺序是升序(little-endian)还是降序(big-endian).

boolIsBigEnd()

{

inti = 1;

return!(*((char*)&i));

}

 

 

9.

String.h:源代码:

 

#ifndefSTRING_H

#defineSTRING_H

 

#include<iostream>

usingnamespace std;

 

classString

{

public:

String();

String(intn,char c);

String(constchar* source);

String(constString& s);

//String&operator=(char* s);

String&operator=(const String& s);

~String();

 

char&operator[](int i){return a[i];}

constchar& operator[](int i) const {return a[i];}//对常量的索引.

String&operator+=(const String& s);

intlength();

 

friendistream& operator>>(istream& is, String& s);//搞清为什么将>>设置为友元函数的原因.

//friendbool operator< (const String& left,const String& right);

friendbool operator> (const String& left, const String& right);//下面三个运算符都没必要设成友元函数,这里是为了简单.

friendbool operator== (const String& left, const String& right);

friendbool operator!= (const String& left, const String& right);

private:

char*a;

intsize;

};

 

#endif

 

 

String.cpp:源代码:

 

 

#include"String.h"

#include<cstring>

#include<cstdlib>

 

String::String(){

a =new char[1];

a[0]= '\0';

size= 0;

}

 

String::String(intn,char c){

a =new char[n + 1];

memset(a,c,n);

a[n]= '\0';

size= n;

}

 

String::String(constchar* source){

if(source== NULL){

a =new char[1];

a[0]= '\0';

size= 0;

}

else

{

size= strlen(source);

a =new char[size + 1];

strcpy(a,source);

}

}

 

String::String(constString& s){

size= strlen(s.a);//可以访问私有变量.

a =new char[size + 1];

//if(a== NULL)

strcpy(a,s.a);

}

 

 

 

String&String::operator=(const String& s){

if(this== &s)

return*this;

else

{

delete[]a;

size= strlen(s.a);

a =new char[size + 1];

strcpy(a,s.a);

return*this;

}

}

 

 

String::~String(){

delete[]a;//是这个析构函数不对还是下面这个+=运算符有问题呢?还是别的原因?

}

 

String&String::operator+=(const String& s){

intj = strlen(a);

size= j + strlen(s.a);

intm = size + 1;

char*b = new char[j+1];

strcpy(b,a);

a =new char[m];

//strcpy(a,b);

inti = 0;

while(i< j){

a[i]= b[i];

i++;

}

delete[] b;

 

int k = 0;

while(j< m){

a[j]= s[k];

j++;

k++;

}

a[j]= '\0';

return*this;

}

 

intString::length(){

returnstrlen(a);

}

 

 

booloperator==(const String& left, const String& right)

{

inta = strcmp(left.a,right.a);

if(a== 0)

returntrue;

else

returnfalse;

}

 

 

booloperator!=(const String& left, const String& right)

{

return!(left == right);

}

 

ostream&operator<<(ostream& os,String& s){

intlength = s.length();

for(inti = 0;i < length;i++)

//os<< s.a[i];这么不行,私有变量.

os<< s[i];

returnos;

}

 

 

Stringoperator+(const String& a,const String& b){

Stringtemp;

temp= a;

temp+= b;

returntemp;

 

}

 

booloperator<(const String& left,const String& right){

 

intj = 0;

while((left[j]!= '\0') && (right[j] != '\0')){

if(left[j]< right[j])

returntrue;

else

{

if(left[j]== right[j]){

j++;

continue;

}

else

returnfalse;

}

}

if((left[j]== '\0') && (right[j] != '\0'))

returntrue;

else

returnfalse;

}

 

booloperator>(const String& left, const String& right)

{

inta = strcmp(left.a,right.a);

if(a> 0)

returntrue;

else

returnfalse;

}

 

istream&operator>>(istream& is, String& s){

delete[]s.a;

s.a= new char[20];

intm = 20;

charc;

inti = 0;

while(is.get(c) && isspace(c));

if(is) {

do {

s.a[i]= c;

i++;

/*if(i>= 20){

cout<< "Input too much characters!" << endl;

exit(-1);

}*/

if(i== m - 1 ){

s.a[i]= '\0';

char*b = new char[m];

strcpy(b,s.a);

m =m * 2;

s.a= new char[m];

strcpy(s.a,b);

delete[]b;

}

}

while(is.get(c) && !isspace(c));

//如果读到空白,将其放回.

if(is)

is.unget();

}

s.size= i;

s.a[i]= '\0';

returnis;

}

 

 

10.有个数组a[100]存放了100个数,这100个数取自1-99,且只有两个相同的数,剩下的98个数不同,写一个搜索算法找出相同的那个数的值.(注意空间效率时间效率尽可能要低).

PS:鉴于以前某人说用int存储数组就是用了O(N)的辅助空间,现在假设是用char存储数组

int GetTheExtraVal(char*var,int size)

{

int val;

int i=0;

for(;i<size;++i)

{

if(var[var[i]&0x7F]&0x80)

{

val=var[i]&0x7F;

break;

}

var[var[i]&0x7F]|=0x80;

}

for(i>=0;--i)

{

var[var[i]&0x7F]&=0x7F;

}

returnval;

}

 

 

(引自http://www.cnblogs.com/omygod/archive/2006/11/15/560786.aspx)

1.是不是一个父类写了一个virtual 函数,如果子类覆盖它的函数不加virtual ,也能实现多态?

virtual修饰符会被隐形继承的。

private也被集成,只事派生类没有访问权限而已

virtual可加可不加

子类的空间里有父类的所有变量(static除外)

同一个函数只存在一个实体(inline除外)

子类覆盖它的函数不加virtual ,也能实现多态。

在子类的空间里,有父类的私有变量。私有变量不能直接访问。

 

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

2.输入一个字符串,将其逆序后输出。(使用C++,不建议用伪码)

#include<iostream>

usingnamespace std;

 

voidmain()

{

  char a[50];memset(a,0,sizeof(a));

  int i=0,j;

  char t;

  cin.getline(a,50,'\n');

 for(i=0,j=strlen(a)-1;i<strlen(a)/2;i++,j--)

  {

   t=a[i];

      a[i]=a[j];

   a[j]=t;

  }

  cout<<a<<endl;

}

//第二种

stringstr;

cin>>str;

str.replace;

cout<<str;

 

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

3.请简单描述Windows内存管理的方法。

内存管理是操作系统中的重要部分,两三句话恐怕谁也说不清楚吧~~

我先说个大概,希望能够抛砖引玉吧

当程序运行时需要从内存中读出这段程序的代码。代码的位置必须在物理内存中才能被运行,由于现在的操作系统中有非常多的程序运行着,内存中不能够完全放下,所以引出了虚拟内存的概念。把哪些不常用的程序片断就放入虚拟内存,当需要用到它的时候在load入主存(物理内存)中。这个就是内存管理所要做的事。内存管理还有另外一件事需要做:计算程序片段在主存中的物理位置,以便CPU调度。

内存管理有块式管理,页式管理,段式和段页式管理。现在常用段页式管理

块式管理:把主存分为一大块、一大块的,当所需的程序片断不在主存时就分配一块主存空间,把程序片断load入主存,就算所需的程序片度只有几个字节也只能把这一块分配给它。这样会造成很大的浪费,平均浪费了50%的内存空间,但时易于管理。

页式管理:把主存分为一页一页的,每一页的空间要比一块一块的空间小很多,显然这种方法的空间利用率要比块式管理高很多。

段式管理:把主存分为一段一段的,每一段的空间又要比一页一页的空间小很多,这种方法在空间利用率上又比页式管理高很多,但是也有另外一个缺点。一个程序片断可能会被分为几十段,这样很多时间就会被浪费在计算每一段的物理地址上(计算机最耗时间的大家都知道是I/O吧)。

段页式管理:结合了段式管理和页式管理的优点。把主存分为若干页,每一页又分为若干段。好处就很明显,不用我多说了吧。

各种内存管理都有它自己的方法来计算出程序片断在主存中的物理地址,其实都很相似。

这只是一个大概而已,不足以说明内存管理的皮毛。无论哪一本操作系统书上都有详细的讲解

 

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

4.

#include"stdafx.h"

#defineSQR(X) X*X

intmain(int argc, char* argv[])

{

 int a = 10;

 int k = 2;

 int m = 1;

 a /= SQR(k+m)/SQR(k+m);

 printf("%d\n",a);

 return 0;

}

这道题目的结果是什么啊?

define只是定义而已,在编择时只是简单代换X*X而已,并不经过算术法则的

a /=(k+m)*(k+m)/(k+m)*(k+m);

=>a/= (k+m)*1*(k+m);

=>a= a/9;

=>a= 1;

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

5.

const符号常量;

(1)constchar *p

(2)charconst *p

(3)char* const p

说明上面三种描述的区别;

 

如果const位于星号的左侧,则const就是用来修饰指针所指向的变量,即指针指向为常量;

如果const位于星号的右侧,const就是修饰指针本身,即指针本身是常量。

(1)constchar *p

一个指向char类型的const对象指针,p不是常量,我们可以修改p的值,使其指向不同的char,但是不能改变它指向非char对象,如:

constchar *p;

charc1='a';

char c2='b';

p=&c1;//ok

p=&c2;//ok

*p=c1;//error

(2)charconst *p

(3)char* const p

这两个好象是一样的,此时*p可以修改,而p不能修改。

(4)constchar * const p

这种是地址及指向对象都不能修改。

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

6.下面是C语言中两种if语句判断方式。请问哪种写法更好?为什么?

 int n;

 if (n == 10) // 第一种判断方式

 if (10 == n) // 第二种判断方式

如果少了个=号,编译时就会报错,减少了出错的可能行,可以检测出是否少了=

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

7.下面的代码有什么问题?

voidDoSomeThing(...)

{

 char* p;

 ...

 p = malloc(1024);  // 分配1K的空间

 if (NULL == p)

  return;

 ...

 p = realloc(p, 2048); // 空间不够,重新分配到2K

 if (NULL == p)

  return;

 ...

}

A:

p =malloc(1024);     应该写成: p = (char *)malloc(1024);

        没有释放p的空间,造成内存泄漏。

 

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

8.下面的代码有什么问题?并请给出正确的写法。

voidDoSomeThing(char* p)

{

 char str[16];

 int n;

 assert(NULL != p);

 sscanf(p, "%s%d", str, n);

 if (0 == strcmp(str, "something"))

 {

  ...

 }

}

A:

sscanf(p,"%s%d", str, n);   这句该写成: sscanf(p,"%s%d", str, &n);

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

9.下面代码有什么错误?

Voidtest1()

{

 char string[10];

 char *str1="0123456789";

 strcpy(string, str1);

}

数组越界

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

10.下面代码有什么问题?

Voidtest2()

{

  char string[10], str1[10];

  for(i=0; i<10;i++)

  {

     str1[i] ='a';

  }

  strcpy(string, str1);

}

数组越界

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

11.下面代码有什么问题?

Voidtest3(char* str1)

{

  char string[10];

  if(strlen(str1)<=10)

  {

    strcpy(string, str1);

  }

}

==数组越界

==strcpy拷贝的结束标志是查找字符串中的\0 因此如果字符串中没有遇到\0的话会一直复制,直到遇到\0,上面的123都因此产生越界的情况

 

建议使用 strncpy 和 memcpy

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

12.下面代码有什么问题?

#defineMAX_SRM 256

DSNget_SRM_no()

{

  static int SRM_no; //是不是这里没赋初值?

  int I;

  for(I=0;I<MAX_SRM;I++,SRM_no++)

  {

    SRM_no %= MAX_SRM;

    if(MY_SRM.state==IDLE)

    {

      break;

    }

  }

  if(I>=MAX_SRM)

    return (NULL_SRM);

  else

    return SRM_no;

}

系统会初始化static int变量为0,但该值会一直保存,所谓的不可重入...

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

13.写出运行结果:

{//test1

    char str[] = "world"; cout<< sizeof(str) << ": ";

    char *p   = str;     cout << sizeof(p)<< ": ";

    char i    = 10;      cout << sizeof(i)<< ": ";

    void *pp  = malloc(10);  cout <<sizeof(p) << endl;

}

6:4:1:4

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

14.写出运行结果:

{//test2

    union V {

 struct X {

  unsigned char s1:2;

  unsigned char s2:3;

  unsigned char s3:3;

 } x;

 unsigned char c;

    } v;

    v.c = 100;

    printf("%d", v.x.s3);

}

3

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

15.用C++写个程序,如何判断一个操作系统是16位还是32位的?不能用sizeof()函数

A1:

16位的系统下,

inti = 65536;

cout<< i; // 输出0;

inti = 65535;

cout<< i; // 输出-1;

32位的系统下,

inti = 65536;

cout<< i; // 输出65536;

inti = 65535;

cout<< i; // 输出65535;

A2:

inta = ~0;

if(a>65536 )

{

    cout<<"32 bit"<<endl;

}

else

{

    cout<<"16 bit"<<endl;

}

 

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

16.C和C++有什么不同?

从机制上:c是面向过程的(但c也可以编写面向对象的程序);c++是面向对象的,提供了类。但是,

c++编写面向对象的程序比c容易

从适用的方向:c适合要求代码体积小的,效率高的场合,如嵌入式;c++适合更上层的,复杂的;  llinux核心大部分是c写的,因为它是系统软件,效率要求极高。

从名称上也可以看出,c++比c多了+,说明c++是c的超集;那为什么不叫c+而叫c++呢,是因为c++比

c来说扩充的东西太多了,所以就在c后面放上两个+;于是就成了c++

C语言是结构化编程语言,C++是面向对象编程语言。

C++侧重于对象而不是过程,侧重于类的设计而不是逻辑的设计。

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

17.在不用第三方参数的情况下,交换两个参数的值

#include<stdio.h>

voidmain()

{

        int i=60;

        int j=50;

        i=i+j;

        j=i-j;

        i=i-j;

       printf("i=%d\n",i);

       printf("j=%d\n",j);

}

方法二:

i^=j;

j^=i;

i^=j;

方法三:

// 用加减实现,而且不会溢出

a = a+b-(b=a)

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

18.有关位域的面试题(为什么输出的是一个奇怪的字符)

a.t= 'b';效果相当于 a.t= 'b' & 0xf;

'b'--> 01100010

'b'& 0xf -->>00000010

所以输出Ascii码为2的特殊字符

 

chart:4;就是4bit的字符变量,同样

unsignedshort i:8;就是8bit的无符号短整形变量

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

19.inti=10, j=10, k=3; k*=i+j; k最后的值是?

60

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

20.进程间通信的方式有?

进程间通信的方式有共享内存, 管道,Socket ,消息队列 , DDE等

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

21.

structA

{

chart:4;

chark:4;

unsignedshort i:8;

unsignedlong m;

}

sizeof(A)=?(不考虑边界对齐)

7

structCELL             // Declare CELL bitfield

{

   unsigned character  : 8; // 00000000 ????????

   unsigned foreground : 3;  // 00000??? 00000000

   unsigned intensity  : 1; // 0000?000 00000000

   unsigned background : 3;  // 0???0000 00000000

   unsigned blink      : 1; // ?0000000 00000000

}screen[25][80];       // Array of bitfields

二、位结构

    位结构是一种特殊的结构, 在需按位访问一个字节或字的多个位时, 位结构

比按位运算符更加方便。

    位结构定义的一般形式为:

     struct位结构名{

          数据类型 变量名: 整型常数;

          数据类型 变量名: 整型常数;

     } 位结构变量;

    其中: 数据类型必须是int(unsigned或signed)。 整型常数必须是非负的整

数, 范围是0~15, 表示二进制位的个数,即表示有多少位。

    变量名是选择项, 可以不命名, 这样规定是为了排列需要。

    例如: 下面定义了一个位结构。

     struct{

          unsigned incon: 8;  /*incon占用低字节的0~7共8位*/

          unsigned txcolor: 4;/*txcolor占用高字节的0~3位共4位*/

          unsigned bgcolor: 3;/*bgcolor占用高字节的4~6位共3位*/

          unsigned blink: 1;  /*blink占用高字节的第7位*/

     }ch;

    位结构成员的访问与结构成员的访问相同。

    例如: 访问上例位结构中的bgcolor成员可写成:

      ch.bgcolor

 

    注意:

    1. 位结构中的成员可以定义为unsigned, 也可定义为signed,  但当成员长

度为1时, 会被认为是unsigned类型。因为单个位不可能具有符号。

    2. 位结构中的成员不能使用数组和指针, 但位结构变量可以是数组和指针,

如果是指针, 其成员访问方式同结构指针。

    3. 位结构总长度(位数), 是各个位成员定义的位数之和,  可以超过两个字

节。

    4. 位结构成员可以与其它结构成员一起使用。

    例如:

     struct info{

          char name[8];

          int age;

          struct addr address;

          float pay;

          unsigned state: 1;

          unsigned pay: 1;

          }workers;

    上例的结构定义了关于一个工人的信息。其中有两个位结构成员, 每个位结

构成员只有一位, 因此只占一个字节但保存了两个信息, 该字节中第一位表示工

人的状态, 第二位表示工资是否已发放。由此可见使用位结构可以节省存贮空间。

 

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

22.下面的函数实现在一个固定的数上加上一个数,有什么错误,改正

intadd_n(int n)

{

  static int i=100;

  i+=n;

  return i;

}

答:

因为static使得i的值会保留上次的值。

去掉static就可了

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

23.下面的代码有什么问题?

classA

{

public:

  A() { p=this; }

  ~A() { if(p!=NULL) { delete p; p=NULL; } }

  A* p;

};

答:

会引起无限递归

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

24.

uniona {

 int a_int1;

 double a_double;

 int a_int2;

};

typedefstruct

{

 a a1;

 char y;

} b;

classc

{

 double c_double;

 b b1;

 a a2;

};

输出cout<<sizeof(c)<<endl;的结果?

答:

VC6环境下得出的结果是32

另:

我(sun)在VC6.0+win2k下做过试验:

short- 2

int-4

float-4

double-8

指针-4

sizeof(union),以结构里面size最大的为union的size

 

1) 不用临时变量完成变量x y的值交换

方法1: x^=y^=x^=y  注意这里异或的使用 当然啦 这个写法要求xy都是unsigned int

方法2: x=x-y; y=x+y;  x=y-x;      无论何种数据格式 只要支持+ -= 通杀

 

2) 写一个宏 不能用if for while 实现求a b的最大值

方法1: #define MAX(a,b)  ((a>b)?(a):(b))    前提是允许使用?:这个3元运算符1

方法2: #define MAX(a,b)  (a+b+abs(a-b))/2  前提是可以使用函数

 

3)  求下列表达式中result的值

inta=-10;

unsignedint b=4;

intc=-5;

intresult=((a+b)>c)?1:-1)

答案是result=1  因为b是unsigned int 那么a+b的时候会进行自动类型转换 将a转换成unsignedint,这样a就变成了一个很大的正数 导致a+b>c

 

答案是result=1  因为b是unsigned int 那么a+b的时候会进行自动类型转换 将a转换成unsignedint,这样a就变成了一个很大的正数 导致a+b>c

 

4) 求下面的程序输出

 class A

{

public:

  A():x(1) {}

   void output() {cout<<"x is"<<x<<endl;}

private:

  int x;

};

 

    class B:public class A

{

public:

  B():x(2) {}

  void output() {cout<<"xis"<<x<<endl; }

private:

  int x;

}

 

intmain()

{

  B tmp;

  A& tmp2=tmp;

  tmp.output();

  tmp2.output();

cout<<sizeof(A)<<sizeof(B)<<endl;

  return 1;

}

 

{

public:

  A():x(1) {}

   void output() {cout<<"x is"<<x<<endl;}

private:

  int x;

};

 

    class B:public class A

{

public:

  B():x(2) {}

  void output() {cout<<"xis"<<x<<endl; }

private:

  int x;

}

 

intmain()

{

  B tmp;

  A& tmp2=tmp;

  tmp.output();

  tmp2.output();

cout<<sizeof(A)<<sizeof(B)<<endl;

  return 1;

}

 

{

public:

  A():x(1) {}

   void output() {cout<<"x is"<<x<<endl;}

private:

  int x;

};

 

classB:public class A

{

public:

  B():x(2) {}

  void output() {cout<<"xis"<<x<<endl; }

private:

  int x;

}

 

intmain()

{

  B tmp;

  A& tmp2=tmp;

  tmp.output();

  tmp2.output();

cout<<sizeof(A)<<sizeof(B)<<endl;

  return 1;

}

 

只需牢记一点 虽然B继承了A, 但是B的成员变量x和A的成员变量x是两个完全不同的变量所以tmp.output()输出的是2 而tmp2.output()输出的是1  sizeof(A)是在编译器就完成计算的 它的值是4(一个int) 而sizeof(B)则是8了

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值