Welcome To Kingsoft
姓名: 林道疆 日期: 2007年8月17日 答题时间:
一、请你就C/C++或者JAVA代码行数、注释行数统计工具的实现,描述一下:
1、 需要考虑哪些过滤条件?你如何处理?
答:过滤条件:(取得每行并去掉两头的空格后)
⑴空行,行的长度为0;⑵如果是以//开头,为注释行;⑶//在行中,并判断不是在字符串中,即“”中,为代码+注释混合行,//在“”中时为代码行;⑷如果/*在行中,判断是否是在“”内,否则为注释行,*/不在“”中时是结束 ;⑸/* */只在一行,判断行中是否有代码,无代码为注释行,有代码是混合行;⑹/* */多行,并且/*前无代码,/*后无代码,去掉其中空行都是注释行;⑺/* */多行,/*在代码后,或*/后有代码,有混合行;⑻一行中有2个/*并且就1个*/,此行为混合行,其后是注释行。
2、 怎样提升这个工具的易用性?
答:把这个工具设置成图形界面,用户只需输入文件名或者在文件对话框中选择文件即可点击运行输出结果。
本题只需要提供思路文档,不需要程序代码。
二、给定一个自然数n,试完成如下程序,它输出不大于n的所有素数(质数)。
1、 请提供程序代码,以及思路文档。
答:思路:求出一个数j的平方根sqrt(j),将j除以2~sqrt(j)之间的数,只要除尽一次,就不是素数,之后数j加2。
#include<stdio.h>
#include<math.h>
void main()
{ int N=1000;
int i,j,k,m=0;
for(j=1;j<N;j=j+2) /*1-N间的素数*/
{ k=(int)sqrt(j); /*求平方根*/
for(i=2;i<=k;i++)
{if(j%i==0) /*只要除尽一次,就不是素数*/
break;
}
if(i>k) /*/除到k一直没除尽,是素数*/
printf("%d ",j);
}
}
3、 请分析一下可以从哪些角度可优化该程序的时间性能?
答:偶数(除了2)不能为素数;判断一个数j是否为素数,只要将其除以2 ~ sqrt(j)之间的素数,更进一步,没有必要对所有奇数进行试除,只需对所有sqrt(j)以内的所有质数试除就可以了。
三、高精度乘法
用户输入两个不大于 256 位的正整数,由程序进行乘法运算,并显示运算过程与结果。例:
输入:12,32
输出:
12
× 32
————————
24
36
————————
384
#include<stdio.h>
#include<stdlib.h>
#include<ctype.h>
#define max 256
int A[max],B[max];
int Alen,Blen;
int S[max *2];
void InputAB() //输入A B
{ int c;
while (!isdigit(c = getchar())) ;
Alen=1;
A[0]= c - '0';
while (isdigit(c = getchar()))
A[Alen++] = c - '0';
while (!isdigit(c = getchar())) ;
Blen = 1;
B[0] = c - '0';
while (isdigit(c = getchar()))
B[Blen++] = c - '0';
}
void Print(int Array[],int len) //输出数组
{ int i=0;
while ((i<len) && (Array[i]== 0) )
i++;
if (i == len)
{ printf(“0 \n”);
return;
}
for ( ;i < len; i++)
printf(“%d”,Array[i]);
printf(“\n”);
}
void Mul(int Array[],int len, int n, int Result[], int zeros) //相乘
{ int i;
for (i = len - 1; i >= 0; i--)
Result[i+1] = Array[i]*n;
Result[0] = 0;
for (i = len; i > 0; i--)
{ if(Result[i] >= 10) //大于10的进位
{ Result[i-1] +=Result[i] / 10;
Result[i] %= 10;
}
}
for (i = 1; i <= zeros; i++)
Result[len+i] = 0;
}
void Add(int total[],int tlen, const int add[], int alen) //各行相加
{ int i,k = tlen;
while ((tlen > 0) && (alen> 0)) //相加
{ tlen--;
alen--;
total[tlen] += add[alen];
}
for (i = k - 1; i>=0; i--)
if(total[i] >= 10) //大于10的进位
{ total[i - 1] += total[i] / 10;
total[i] %= 10;
}
}
void main()
{ int i,j;
int temp[max*2];
InputAB();
Print(A,Alen);
printf(“*”);
Print(B,Blen);
printf("-----\n");
for(i = Blen-1; i >= 0; i--)
{ for(j=Blen-i,j>=0;j--)//输出空格
{ printf(“ ”);
}
Mul(A, Alen, B[i], temp, Blen -1 -i);//B中的一个数与A的所有数相乘
Print(temp, Alen + 1); //输出相乘过程中的每行
Add(S, max*2, temp, Alen + Blen- i);//每行相加
}
printf("-----\n");
Print(S, max*2);
}
}四、输入一个N进制数,将其转换成 M 进制数(1<N<=16,1<M<=16)
#include <iostream.h>
#include <stdio.h>
#include <stack.h>
#include <assert.h>
#include <math.h>
using namespace std;
int main()
{
char digit[16] = {0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F};
cout <<"输入待转换整数: ";
char c;
char a[80];
char b[80];
int i=0,j=0,length;
while ((c = getchar())!='\n') //输入
{a[i]=c;
i++;
}
length=i; //输入的数的位数 0~i-1
for(j=0;j<length;j++) //转化成数值
{ if( a[j]>='0'&&a[j]<='9')
b[j] = a[j] -'0';
else if( a[j]>='a'&&a[j]<='f' )
b[j] = a[j] -'a' +10;
else if( a[j]>='A'&&a[j]<='F' )
b[j]= a[j] -'A' +10;
else
return FALSE;
}
cout<<"输入的数是多少进制N:";
int n
cin>>n;
assert((n>1)&&(n<=16));
int num=0;
for(i=0,j=length-1;j>=0;j--,i++)//输入的数转成十进制
{num+=b[i]*pow(n,j);
}
cout <<"转换成进制数M: ";
int m;
cin >>m;
cout <<endl;
assert((m>1)&&(m<=16));
stack<char> stk;
char remain;
while (num!=0)//转成M进制
{
remain = digit[num%m];
stk.push(remain);
num/=m;
}
cout <<"结果: ";//输出结果
while(!stk.empty())
{
cout <<stk.top();
stk.pop();
}
cout <<endl;
return 0;
}
五、选答题(以下任选一题):
1、构建一个应用程序,它可以显示剪贴板上所有可用的格式,并且将常规格式(如文本、图形)显示出来。
2、构建一个应用程序,它用于显示一幅透明位图。即,给定一个背景图、一个待显示位图和一个对应于该位图的屏蔽(mask)图,将位图未屏蔽部分显示在背景图上。
3、构造一个服务端程序和一个客户端程序。它用于通过网络将文件从服务端传送到客户机(类似FTP)。或者直接是一个FTP客户端程序也可,不能使用FTP控件。
4、构造一个应用程序,它定时获取CPU利用率,并且以折线图的方式动态显示出来。
5、利用UDP把一个文件从一台机器传送到另一台机器。
6、在某文件中查找指定的单词,把所有包含此单词的文本行打印出来,并对找到的单词作着重显示(如下划线或其他显示方式)的处理。
6:
#include <fstream.h>
#include <iostream.h>
#include <string.h>
#include <vector.h>
#include <algorithm.h>
#include <ctype.h>
using namespace std;
int word_find(const char t[], int m, const char s[],int n ,vector<int>& colpos)
//查找单词,char t[]为单词,m单词长度,char s[]为行,n行的长度,colpos记录找到单词所在的位置
{ inti=0,j=0,cnt=0;
while(j<n)//j为行下标,i为单词串下标
{ if(i >= m)
{ if(!isalpha(s[j])&&!isalpha(s[j-m-1]))//字符串前后不是字母时是单词
{ colpos[cnt++] = j - m ;//单词的第一个字符所在的行下标
i=0; //单词串下标重置为0
if(cnt == colpos.size())
colpos.resize(cnt * 2);//长度重设为原来2倍
}
else { i=0; }
}
else if (s[j]==t[i])
{ ++i;++j; }
else
{ j=j-i+1; i=0; } //下标后退重新开始匹配
}
returncnt;//返回查到的个数
}
int count_string(string source, string target,vector<int>& colpos)
{ int find_cnt = 0;
find_cnt =word_find(target.c_str(), target.size(), source.c_str(),source.size(),colpos);
returnfind_cnt;//返回查到的个数
}
int main()
{
string file_name, line;
vector<string> lines;
lines.resize(10);
cout << "Input the file name:";
cin >>file_name;
ifstream in_file; //打开文件
try{
in_file.open(file_name.c_str());
if(!in_file)
throw(file_name);
}
catch(stringfile_name)
{ cout<< "Fatal error: File not found."<<endl;
exit(1);
}
int line_count = 0;//文件行数
do{
getline(in_file, lines[line_count]);
line_count++;
if(line_count == lines.size())//未结束时行数设为原来2倍
lines.resize(line_count * 2);
}while(in_file.eof()==0);
string tag;//要查找的单词
vector<int> colpos;//单词中第一个字符所在位置
colpos.resize(10);
do
{
cout<< "Input the word you want to find(# for quit):";//输入要查找的单词#结束
cin >>tag;
if(tag =="#")
{ break; }
int count =0, line_no = 0 , inline_count;//line_no是行号,第?行
for(line_no= 0 ;line_no < line_count ; line_no++)
{
inline_count = count_string(lines[line_no],tag, colpos);//每行查到的个数
count += inline_count; //查到的总数
if(inline_count> 0)
{
cout << "在第" <<line_no<<"行找到"<< inline_count<<"个"<<tag;
cout << " ,所在位置是 ";
for(inti = 0 ;i< inline_count ;i++)
{
cout << colpos<< ' ';//输出位置
}
cout<< endl;
cout<< lines[line_no] << endl;//输出行,未作着重显示
}
}
}while(tag !="#");
in_file.close();
return 0;
}