其他公司笔试题大全
其他公司笔试题大全
重入的概念
两个线程重复进入同一方法
在实时系统的设计中,经常会出现多个任务调用同一个函数的情况。如果这个函数不幸被设计成为不可重入的函数的话,那么不同任务调用这个函数时可能修改其他任务调用这个函数的数据,从而导致不可预料的后果。那么什么是可重入函数呢?
所谓可重入函数是指一个可以被多个任务调用的过程,任务在调用时不必担心数据是否会出错。不可重入函数在实时系统设计中被视为不安全函数。
满足下列条件的函数多数是不可重入的:
(1)函数体内使用了静态的数据结构;
(2)函数体内调用了malloc()或者free()函数;
(3)函数体内调用了标准I/O函数。
下面举例加以说明。
可重入函数
void strcpy(char* lpszDest, char* lpszSrc)
{
while(*lpszDest++ = *lpszSrc++);
*dest=0;
}
非可重入函数1
char cTemp; // 全局变量
void SwapChar1(char* lpcX, char* lpcY)
{
cTemp = *lpcX;
*lpcX = *lpcY;
lpcY = cTemp; // 访问了全局变量,在分享内存的多个线程中可能造成问题
}
非可重入函数2
void SwapChar2(char* lpcX, char* lpcY)
{
static char cTemp;// 静态局部变量
cTemp = *lpcX;
*lpcX = *lpcY;
lpcY = cTemp; // 使用了静态局部变量,在分享内存的多个线程中可能造成问题
}
如何写出可重入的函数?在函数体内不访问那些全局变量,不使用静态局部变量,坚持只使用局部变量,写出的函数就将是可重入的。如果必须访问全局变量,记住利用互斥信号量来保护全局变量。:)
嵌入式操作系统和通用操作系统有什么差别?
1.多为实时操作系统!
2.分时操作系统!
不使用> < ?:运算符,求a,b中较大的一个
max=(a+b+abs(a-b))/2;
1 构造函数可不可以是虚函数,为什么?
不可以需函数的调用必须要有V_TABLE的支持,当在构造函数中的时候, 对象还没有构造完成,是没有这个表的,所以无法调用虚函, 而析构函调用的时候,很显然,对象已经构造完毕.!
有错误,是vptr没有被初始化
2 析构函数可不可以是虚函数,为什么?
可以 虚析构函数
3 构造函数没有返回值,怎么确定是否成功?
失败则抛出一个异常,或者使用一个内部状态位标识对象状态
4 析构函数内为什么不能抛出异常?
throw 会使栈被展开,因为在栈展开时,栈页面中的所有的局部对象会被析构,此时如果那些析构函数之一抛出异常,C++运行时系统会无法判断该如何处理。
5 类的成员函数作回调函数需要什么条件?
关键就是不让this指针起作用
回调函数使用方法:
a. 直接使用普通C函数
b. 使用静态成员函数
6 VERIFY和ASSERT有什么异同
ASSERT宏只在调试版本中才会有作用,VERIFY在发行版本中同样会起作用,但是使用VERIFY会导致非常不友好的用户界面。
7 优化数据库有哪些方法?
a、关键字段建立索引。
b、使用存储过程,它使SQL变得更加灵活和高效。
c、备份数据库和清除垃圾数据。
d、SQL语句语法的优化。
e、清理删除日志。
8当前软件业发展困难?
资金困难,管理理论,技术落后,使软件企业无法承受软件开发方面的投入与产出的不成比例
就是有4个人,其中有一个是小偷,对这4个人调查,他们又说真话有说假话的,叫你编程实现打印出谁是小偷。。
具体题目记不得了;
类似于:
甲,乙,丙,丁有人说真话,有人说假话
甲:乙偷了,丁没偷
乙:甲没偷,丙没偷
丙:丁偷了,我没偷
丁:我没偷
叫你打印出谁是小偷
呵呵,可能不合逻辑哦,反正是这样的题,离散书里都有,不过暂时找不到准确的例题。。
大家给个解题思路吧
具体题目记不得了;
类似于:
甲,乙,丙,丁有人说真话,有人说假话
甲:乙偷了,丁没偷
乙:甲没偷,丙没偷
丙:丁偷了,我没偷
丁:我没偷
叫你打印出谁是小偷
呵呵,可能不合逻辑哦,反正是这样的题,离散书里都有,不过暂时找不到准确的例题。。
大家给个解题思路吧
#include <iostream.h>
#include <stdlib.h>
//-1。未表态,0。没偷,1。偷了
int matrix[4][4]={-1,1,-1,0,
0,-1,0,-1,
-1,-1,0,1,
-1,-1,-1,0};
int fact[4][4];
void output(int a[][4])
{
for(int i=0;i<4;i++)
{
for(int j=0;j<4;j++)
cout<<" "<<a[i][j];
cout<<endl;
}
cout<<endl;
}
//判断是否和逻辑,即既有说真话的,也有说假话的
int judge()
{
int iRight=0;
int iWrong=0;
for(int i=0;i<4;i++)
{
int iRW=0;
for(int j=0;j<4;j++)
{
if(matrix[i][j]!=-1)
{
if(matrix[i][j]!=fact[i][j])
goto wrong;
}
}
iRW=1;
wrong: if(iRW)iRight++;
else
iWrong++;
}
if(iRight==0 && iWrong==0)return 0;
else return 1;
}
int main(int argc, char *argv[])
{
for(int i=0;i<4;i++)
{
//假设第i个人偷的
for(int j=0;j<4;j++)
fact[j][i]=1;
output(fact);
if(judge())cout<<"That's OK!"<<endl;
//判断
//恢复
for(j=0;j<4;j++)
fact[j][i]=0;
}
system("PAUSE");
return 0;
}
2 将一个文件按行排序,比较每行的第一个字符,字符小的靠前,相同则比较下一个字符,存储结果到新文件
分为两种情况,
如果文件比较小,可以放在内存中处理,就很简单,将文件一次性读入内存,放到一个大的空间中,扫描文件,将一个指针数组指向每一行的行首,同时在这个过程中将换行符'/n'换成'/0',然后利用字符串数组进行排序,这样不需要移动字符串本身。最后将结果写入新文件。
先算出有多少行,然后char str[num][256];
用fgets逐行读取,存放到str中,定义char *ptr[num],存放位置
如果文件较大不可能放入内存中,就只在内存中建立长整形数组(可以使用malloc,这样可以申请到比较大的空间),扫描文件,将数组中的值设置为每一行在文件中出现的位置,排序后输出,这个方法比第一种慢得多,因为排序过程中要读文件。