2014年华为上机题及代码

http://blog.csdn.net/dalianmaoblog/article/details/11477997


题目来源于http://blog.csdn.net/hackbuteer1/article/details/11132567

后面的代码是今天早上才写的,C++好长时间不写了,一些简单的函数都是上网查的用法,如果要我现场写,估计很悬。

华为2014校园招聘的机试题目和2013年的完全一样。
一、题目描述(60分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串过滤程序,若字符串中出现多个相同的字符,将非首次出现的字符过滤掉。
比如字符串“abacacde”过滤结果为“abcde”。

要求实现函数:void stringFilter(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
            lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;
 

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“deefd”        输出:“def”
输入:“afafafaf”     输出:“af”
输入:“pppppppp”     输出:“p”

main函数已经隐藏,这里保留给用户的测试入口,在这里测试你的实现函数,可以调用printf打印输出
当前你可以使用其他方法测试,只要保证最终程序能正确执行即可,该函数实现可以任意修改,但是不要改变函数原型。一定要保证编译运行不受影响。

  1. void stringFilter(const char *pInputStr, long lInputLen, char *pOutputStr){  
  2.    map<char,int> charMap;  
  3.    int k=0;  
  4.    for(int i=0;i<lInputLen;i++){  
  5.       if(charMap.find(*(pInputStr+i))==charMap.end()){  
  6.           *(pOutputStr+k++)=*(pInputStr+i);  
  7.           charMap.insert(pair<char,int>(*(pInputStr+i),1));  
  8.       }  
  9.    }  
  10.    *(pOutputStr+k++)='\n';  
  11. }  


二、题目描述(40分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串压缩程序,将字符串中连续出席的重复字母进行压缩,并输出压缩后的字符串。
压缩规则:
1、仅压缩连续重复出现的字符。比如字符串"abcbc"由于无连续重复字符,压缩后的字符串还是"abcbc"。
2、压缩字段的格式为"字符重复的次数+字符"。例如:字符串"xxxyyyyyyz"压缩后就成为"3x6yz"。

要求实现函数: 
void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
            lInputLen:  输入字符串长度
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“cccddecc”   输出:“3c2de2c”
输入:“adef”     输出:“adef”
输入:“pppppppp” 输出:“8p”

  1. void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr){  
  2.        int k=0;  
  3.        for(int i=0;i<lInputLen;i++){  
  4.           int num=1;  
  5.           int j=i+1;  
  6.           for(;j<lInputLen;j++){  
  7.             if(pInputStr[j]==pInputStr[i]){  
  8.                 num++;  
  9.             }else{  
  10.                 break;  
  11.             }  
  12.           }  
  13.           if(num!=1){  
  14.               char str[100];  
  15.               sprintf(str,"%d",num);  
  16.               strcpy(pOutputStr+k,str);  
  17.               k = k+strlen(str);  
  18.           }  
  19.           *(pOutputStr+k++)=*(pInputStr+i);  
  20.           i = j-1;  
  21.        }  
  22.        *(pOutputStr+k++)='\n';  
  23. }  

三、题目描述(50分): 
通过键盘输入100以内正整数的加、减运算式,请编写一个程序输出运算结果字符串。
输入字符串的格式为:“操作数1 运算符 操作数2”,“操作数”与“运算符”之间以一个空格隔开。

补充说明:
1、操作数为正整数,不需要考虑计算结果溢出的情况。
2、若输入算式格式错误,输出结果为“0”。

要求实现函数: 
void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
            lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;
 

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“4 + 7”  输出:“11”
输入:“4 - 7”  输出:“-3”
输入:“9 ++ 7”  输出:“0” 注:格式错误

  1. bool isOperater(char* c){  
  2.       char f[]="+-*/";  
  3.       if(c==NULL||strlen(c)!=1){  
  4.          return false;  
  5.       }  
  6.       for(int i=0;i<strlen(f);i++){  
  7.           if(f[i]==*c)  
  8.               return true;  
  9.       }  
  10.       return false;  
  11. }  
  12.   
  13. bool isNumber(char* c,int& num){  
  14.       if(c==NULL||strlen(c)<=0){  
  15.          return false;  
  16.       }  
  17.   
  18.       for(int i=0;i<strlen(c);i++){  
  19.           if(c[i]>'9'||c[i]<'0')  
  20.               return false;  
  21.       }  
  22.       num = atoi(c);  
  23.       return true;  
  24. }  
  25.   
  26. struct data{  
  27. public:  
  28.    bool isNum;  
  29.    union{  
  30.        char operater;  
  31.        int number;  
  32.    }u;  
  33. };  
  34.   
  35. void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr){  
  36.     stack<data> Stack;  
  37.     const char *d = " ";  
  38.     char s[256];  
  39.     strcpy(s,pInputStr);  
  40.     char *p;  
  41.     int num;  
  42.     p = strtok(s,d);  
  43.     while(p){  
  44.        if(isOperater(p)){ //是操作符  
  45.             if(Stack.size()<1){  
  46.                 strcpy(pOutputStr,"0"); //格式错误  
  47.                 return;  
  48.             }else{  
  49.                 data data1= Stack.top();  
  50.                 if(data1.isNum){ //栈顶元素是数字  
  51.                     data data2;  
  52.                     data2.isNum = false;  
  53.                     data2.u.operater=*p;  
  54.                     Stack.push(data2);  
  55.                 }else{//栈顶元素是操作符  
  56.                     strcpy(pOutputStr,"0"); //格式错误  
  57.                     return;  
  58.                 }  
  59.             }  
  60.        }else if(isNumber(p,num)){ //是数字  
  61.            if(Stack.size()<1){  
  62.                 data data1;  
  63.                 data1.isNum = true;  
  64.                 data1.u.number=num;  
  65.                 Stack.push(data1);  
  66.            }else{  
  67.                 data data1= Stack.top();  
  68.                 if(data1.isNum){ //栈顶元素是数字  
  69.                     strcpy(pOutputStr,"0"); //格式错误  
  70.                     return;  
  71.                 }else{//栈顶元素是操作符  
  72.                     Stack.pop();  
  73.                     data data2 = Stack.top();  
  74.                     Stack.pop();  
  75.                     if(!data2.isNum){  
  76.                         strcpy(pOutputStr,"0"); //格式错误  
  77.                         return;  
  78.                     }  
  79.                     int num2 = data2.u.number;  
  80.                     int num3 = 0;  
  81.                      switch(data1.u.operater){  
  82.                        case '+':  
  83.                            num3=num2+num;  
  84.                            break;  
  85.                        case '-':  
  86.                            num3=num2-num;  
  87.                            break;  
  88.                        case '*':  
  89.                            num3=num2*num;  
  90.                            break;  
  91.                        case '/':  
  92.                            num3=num2/num;  
  93.                            break;  
  94.                        default:  
  95.                            strcpy(pOutputStr,"0"); //格式错误  
  96.                            return;  
  97.                        }  
  98.                      data data3;  
  99.                      data3.isNum=true;  
  100.                      data3.u.number=num3;  
  101.                      Stack.push(data3);  
  102.                 }  
  103.            }  
  104.        }else{  
  105.            strcpy(pOutputStr,"0"); //格式错误  
  106.            return;  
  107.        }  
  108.        p=strtok(NULL,d);  
  109.     }  
  110.     if(Stack.size()==1){  
  111.         data d = Stack.top();  
  112.         if(d.isNum){  
  113.             sprintf(pOutputStr,"%d",d.u.number);  
  114.             return;  
  115.         }  
  116.     }  
  117.    strcpy(pOutputStr,"0"); //格式错误  
  118.    return;  
  119. }  

整个源码:

  1. //============================================================================  
  2. // Name        : huaweijishi.cpp  
  3. // Author      :   
  4. // Version     :  
  5. // Copyright   : Your copyright notice  
  6. // Description : Hello World in C++, Ansi-style  
  7. //============================================================================  
  8.   
  9. #include <iostream>  
  10. #include <map>  
  11. #include <string.h>  
  12. #include <stdlib.h>  
  13. #include <stdio.h>  
  14. #include <stack>  
  15.   
  16. using namespace std;  
  17.   
  18. void stringFilter(const char *pInputStr, long lInputLen, char *pOutputStr){  
  19.    map<char,int> charMap;  
  20.    int k=0;  
  21.    for(int i=0;i<lInputLen;i++){  
  22.       if(charMap.find(*(pInputStr+i))==charMap.end()){  
  23.           *(pOutputStr+k++)=*(pInputStr+i);  
  24.           charMap.insert(pair<char,int>(*(pInputStr+i),1));  
  25.       }  
  26.    }  
  27.    *(pOutputStr+k++)='\n';  
  28. }  
  29.   
  30. void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr){  
  31.        int k=0;  
  32.        for(int i=0;i<lInputLen;i++){  
  33.           int num=1;  
  34.           int j=i+1;  
  35.           for(;j<lInputLen;j++){  
  36.             if(pInputStr[j]==pInputStr[i]){  
  37.                 num++;  
  38.             }else{  
  39.                 break;  
  40.             }  
  41.           }  
  42.           if(num!=1){  
  43.               char str[100];  
  44.               sprintf(str,"%d",num);  
  45.               strcpy(pOutputStr+k,str);  
  46.               k = k+strlen(str);  
  47.           }  
  48.           *(pOutputStr+k++)=*(pInputStr+i);  
  49.           i = j-1;  
  50.        }  
  51.        *(pOutputStr+k++)='\n';  
  52. }  
  53.   
  54.   
  55.   
  56. bool isOperater(char* c){  
  57.       char f[]="+-*/";  
  58.       if(c==NULL||strlen(c)!=1){  
  59.          return false;  
  60.       }  
  61.       for(int i=0;i<strlen(f);i++){  
  62.           if(f[i]==*c)  
  63.               return true;  
  64.       }  
  65.       return false;  
  66. }  
  67.   
  68. bool isNumber(char* c,int& num){  
  69.       if(c==NULL||strlen(c)<=0){  
  70.          return false;  
  71.       }  
  72.   
  73.       for(int i=0;i<strlen(c);i++){  
  74.           if(c[i]>'9'||c[i]<'0')  
  75.               return false;  
  76.       }  
  77.       num = atoi(c);  
  78.       return true;  
  79. }  
  80.   
  81. struct data{  
  82. public:  
  83.    bool isNum;  
  84.    union{  
  85.        char operater;  
  86.        int number;  
  87.    }u;  
  88. };  
  89.   
  90. void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr){  
  91.     stack<data> Stack;  
  92.     const char *d = " ";  
  93.     char s[256];  
  94.     strcpy(s,pInputStr);  
  95.     char *p;  
  96.     int num;  
  97.     p = strtok(s,d);  
  98.     while(p){  
  99.        if(isOperater(p)){ //是操作符  
  100.             if(Stack.size()<1){  
  101.                 strcpy(pOutputStr,"0"); //格式错误  
  102.                 return;  
  103.             }else{  
  104.                 data data1= Stack.top();  
  105.                 if(data1.isNum){ //栈顶元素是数字  
  106.                     data data2;  
  107.                     data2.isNum = false;  
  108.                     data2.u.operater=*p;  
  109.                     Stack.push(data2);  
  110.                 }else{//栈顶元素是操作符  
  111.                     strcpy(pOutputStr,"0"); //格式错误  
  112.                     return;  
  113.                 }  
  114.             }  
  115.        }else if(isNumber(p,num)){ //是数字  
  116.            if(Stack.size()<1){  
  117.                 data data1;  
  118.                 data1.isNum = true;  
  119.                 data1.u.number=num;  
  120.                 Stack.push(data1);  
  121.            }else{  
  122.                 data data1= Stack.top();  
  123.                 if(data1.isNum){ //栈顶元素是数字  
  124.                     strcpy(pOutputStr,"0"); //格式错误  
  125.                     return;  
  126.                 }else{//栈顶元素是操作符  
  127.                     Stack.pop();  
  128.                     data data2 = Stack.top();  
  129.                     Stack.pop();  
  130.                     if(!data2.isNum){  
  131.                         strcpy(pOutputStr,"0"); //格式错误  
  132.                         return;  
  133.                     }  
  134.                     int num2 = data2.u.number;  
  135.                     int num3 = 0;  
  136.                      switch(data1.u.operater){  
  137.                        case '+':  
  138.                            num3=num2+num;  
  139.                            break;  
  140.                        case '-':  
  141.                            num3=num2-num;  
  142.                            break;  
  143.                        case '*':  
  144.                            num3=num2*num;  
  145.                            break;  
  146.                        case '/':  
  147.                            num3=num2/num;  
  148.                            break;  
  149.                        default:  
  150.                            strcpy(pOutputStr,"0"); //格式错误  
  151.                            return;  
  152.                        }  
  153.                      data data3;  
  154.                      data3.isNum=true;  
  155.                      data3.u.number=num3;  
  156.                      Stack.push(data3);  
  157.                 }  
  158.            }  
  159.        }else{  
  160.            strcpy(pOutputStr,"0"); //格式错误  
  161.            return;  
  162.        }  
  163.        p=strtok(NULL,d);  
  164.     }  
  165.     if(Stack.size()==1){  
  166.         data d = Stack.top();  
  167.         if(d.isNum){  
  168.             sprintf(pOutputStr,"%d",d.u.number);  
  169.             return;  
  170.         }  
  171.     }  
  172.    strcpy(pOutputStr,"0"); //格式错误  
  173.    return;  
  174. }  
  175.   
  176.   
  177.   
  178. int main() {  
  179.   
  180.     char r[256];  
  181.     int a = atoi("a");  
  182.     char* p="abcddcae";  
  183.     stringFilter(p,strlen(p),r);  
  184.     cout<<"原字符串:"<<p<<endl;  
  185.     cout<<"转换后的字符串:"<<r<<endl;  
  186.   
  187.     p = "aaabbbcceffggh";  
  188.     stringZip(p,strlen(p),r);  
  189.     cout<<"原字符串:"<<p<<endl;  
  190.     cout<<"转换后的字符串:"<<r<<endl;  
  191.   
  192.     p = "1 + 2";  
  193.     arithmetic(p,strlen(p),r);  
  194.     cout<<"原字符串:"<<p<<endl;  
  195.     cout<<"转换后的字符串:"<<r<<endl;  
  196.   
  197.     p = "1a + 2";  
  198.     arithmetic(p,strlen(p),r);  
  199.     cout<<"原字符串:"<<p<<endl;  
  200.     cout<<"转换后的字符串:"<<r<<endl;  
  201.   
  202.     p = "1 + 2 * 3";  
  203.     arithmetic(p,strlen(p),r);  
  204.     cout<<"原字符串:"<<p<<endl;  
  205.     cout<<"转换后的字符串:"<<r<<endl;  
  206.     return 0;  
  207. }  

 

2014年华为上机题一

此题是2013年9月14日本人参加上机考试的题目

1、第一题的题目大概是输入整型数组求数组的最小数和最大数之和,例如输入1,2,3,4则输出为5,当输入只有一个数的时候,则最小数和最大数都是该数,例如只输入1,则输出为2;另外数组的长度不超过50

以下答案是本人写的,已经在vs2008上测试通过,如果有更简便的方法还请提出来。

()先贴一个错误的做法:

#include<iostream>
using namespace std;
int main()
{
 int n;
 cout<<"请输入数组的长度:"<<endl;
 cin>>n;
 int *p=new int[n];
 for(int i=0;i<n;i++){
  cin>>p[i];
  //cin>>
 }
 int max_num=p[0],min_num=p[0];
 cout<<"数组的输出: "<<endl;
 for(int i=0;i<n;i++){
  //cout<<p[i]<<endl;
  if(max_num<=p[i]){
   max_num=p[i];
  }
  if(min_num>=p[i]){
   min_num=p[i];
  }
  if(i==n-1){
   cout<<max_num+min_num<<endl;
  }
 }
 delete[]p;
 return 0;
}

(2)比较正确的做法

#include<iostream>
#include<string>
using namespace std;

int main(){
 string s;
 int temp=0;  //将字符转换成数字
 int num[50]={0};
 int i=0;
 char *p;
 cin>>s;  //输入字符串
 //p=s;
    cout<<s<<endl;
 for(string::size_type ix=0;ix!=s.size();++ix){
  if(s[ix]!=','){
   temp=temp*10+s[ix]-'0';
  }
  else{
   num[i]=temp;
   temp=0;
   cout<<num[i]<<endl;
   i++;
  }
  
  
 }
 //最后一个没有逗号的数字 
 num[i]=temp;
  cout<<num[i]<<endl;

//计算数组中的最大,最小数之和
  int min_num=num[0];
  int max_num=num[0];
  for(int j=0;j<=i;j++){
            if(num[j]>=max_num)
    max_num=num[j];
   if(num[j]<=min_num)
    min_num=num[j];

  }
  cout<<min_num+max_num;

   return 0;
 }

需要指出的是,输入的控制,这里面第一眼大家都会想到用数组,但是数组的长度是不知道的,无法控制输入,所以很容易陷进去,而用字符串则直接回车后便退出控制台。

2 求两个长长整型的数据的和并输出,例如输入1233333333333333 。。。 3111111111111111111111111.。。。,则输出。。。。

此题同样是采用字符串类似的方法,本文此处用的是char 型指针,用纯C做的,代码不够简洁,还请大家多批评指正。

#include<stdio.h>
#include<string.h>
#include<malloc.h>
void main()
{
  char *p;  //输入数字字符串1
  char *q;  //输入数字字符串2
  char *sum; //求和的字符串
  int p_len; //数字字符串1的长度
  int q_len; //数字字符串2的长度
  //int len;
  int len;
  int len_temp; //两个字串的最大长度
  int xunhuan;  //相加循环的次数
  int index=0;   //求和之后的进位
  int d;   //求和
  int bit;
  int i;
  int p_bit;    //p的每位
  int q_bit;   //q的每位
  //char *temp;
  p=(char*)malloc(sizeof(char));
  q=(char*)malloc(sizeof(char));
  sum=(char*)malloc(sizeof(char));
  sum[0]='0';   //初始化进位
  scanf("%s",p);
  scanf("%s",q);
  p_len=strlen(p);
  q_len=strlen(q);
  if(p_len==q_len){
     len=p_len;
  for(i=len;i>0;i--){
   p_bit=p[i-1]-'0';
   q_bit=q[i-1]-'0';
   d=(q_bit+p_bit+index)%10;
   index=(q_bit+p_bit+index)/10;
   sum[i]=d+'0';
  }
  if(index!=0){
   sum[0]=index+'0';
  }
  sum[len+1]='\0';
   if(sum[0]=='0')
    printf("%s",sum+1);
   else
    printf("%s",sum);

  }
  if(p_len!=q_len)
  {
   len_temp=(p_len>q_len)?p_len:q_len;
  xunhuan=(p_len>q_len)?q_len:p_len;
  if(len_temp==p_len){
   strcpy(sum+1,p);
  }
  else{
   strcpy(sum+1,q);
  }
   len=len_temp+1;
   for(i=xunhuan;i>=1;i--){
    if(p_len>q_len){
    p_bit=p[len_temp-1]-'0';
    q_bit=q[i-1]-'0';
    }
    else{
     p_bit=p[i-1]-'0';
     q_bit=q[len_temp-1]-'0';
    }
    d=(q_bit+p_bit+index)%10;
    index=(q_bit+p_bit+index)/10;
    sum[len_temp--]=d+'0';
   }
   while(index==1){
    bit=sum[len_temp]-'0';
    d=(bit+index)%10;
    index=(bit+index)/10;
   // sum[len_temp]=(((sum[len_temp]-'0')+index)/10)+'0';
   // index=(index+(sum[len_temp]-'0'))%10;
   sum[len_temp]=d+'0';
    len_temp--;
   }
   sum[len]='\0';
     if(sum[0]=='0')
   printf("%s",sum+1);
  else
   printf("%s",sum);
  
  }
}



 

2014华为校园招聘 机试 第三题

根据网传的2014华为校园招聘的机试题目,而编写的代码。

/*
输入一个二叉树 格式为“单个字符+节点所在层次” 
比如根节点所在层次是1,它的两个子树都是2. 节点排列从左到右,然后再输入其中的某个(些)节点,
求得其深度。
第三题还有条件:层次不超过9层
输入:a1b2c2d3e3f3    ab
输出:3 2

[输入、输出有点随意]
*/

#include <iostream>
#include <queue>
#include <string>
#include <vector>
using namespace  std;

static int maxLevel = 1;
struct Node
{
char ch;
int level;
Node* pLeft;
Node* pRight;

Node(char c, int level)
{
ch = c;
this->level = level;
pLeft = NULL;
pRight = NULL;
}
};

//每次添加新节点时, 将当前的树 按层次遍历添加到队列中
void InitialQueue(queue<Node*>& que, Node* pFirst)
{
que.push(pFirst);
queue<Node*> tempQue;
tempQue.push(pFirst);   //申请一个临时用于 操作的队列
while(pFirst)
{
if (pFirst->pLeft !=NULL)
{
que.push(pFirst->pLeft);
tempQue.push(pFirst->pLeft);
}
if (pFirst->pRight != NULL)
{
que.push(pFirst->pRight);
tempQue.push(pFirst->pRight);
}
tempQue.pop();

if (tempQue.empty())
{
break;
}
pFirst =  tempQue.front();
}
return;
};

Node* CreateTree(char* source)
{
Node  *pRoot = new Node(source[0], source[1]-48);
char* pCopy = source+2;

while (*pCopy != '\0')
{
queue<Node*>  que;
InitialQueue(que, pRoot);   //层次遍历整个二叉树
char ch = *pCopy;
int level = *(++pCopy)-48;
Node*  pNewNode = new Node(ch, level);

while (!que.empty())    //队列不为空
{
Node* queNode = que.front();
if(queNode->level == pNewNode->level -1)     //此节点为 待插入节点的上层节点
{
if (queNode->pLeft ==NULL)
{
queNode->pLeft = pNewNode;
que.push(pNewNode);
break;

}else if (queNode->pRight == NULL)
{
queNode->pRight = pNewNode;
que.push(pNewNode);
break;

}else //此上层节点左右孩子已满,弹出
{
que.pop(); 
}
}else //若不为上层节点,弹出
{
que.pop();         
}
}
pCopy++;
}
return pRoot;
}

//获得输入节点在树中的位置

Node* GetPointer(Node* pRoot, char test)
{
queue<Node*> que;
que.push(pRoot);

while (pRoot)
{
if (pRoot->ch == test)
{
return pRoot;
}
if(pRoot->pLeft)
{
if (pRoot->ch == test)
{
return pRoot->pLeft;

}else
{
que.push(pRoot->pLeft);
}
}
if (pRoot->pRight)
{
if (pRoot->pRight->ch == test)
{
return pRoot->pRight;

}else
{
que.push(pRoot->pRight);
}
}
que.pop();      //注意对 队列为空的判断!
if (que.empty())
{
break;
}
pRoot = que.front();
}
return NULL;
}

//找到以输入节点为根节点的树的最大层数
int Ergodic(Node* pNode)
{

if (pNode == NULL)
{
return -1;
}

if (pNode->pLeft != NULL)
{
Ergodic(pNode->pLeft);
maxLevel = max(maxLevel, pNode->pLeft->level);
}

if (pNode->pRight != NULL)
{
Ergodic(pNode->pRight);
maxLevel = max(maxLevel, pNode->pRight->level);
}

return max(maxLevel, pNode->level);
}

vector<int> GetLevel(char* input, char* test)
{
//@1 构建树
vector<int> vec;
Node *pRoot = CreateTree(input);


//@2 找到输入节点在树中的位置
while (*test  !='\0')
{
char ch = *test;
Node* pPointer = GetPointer(pRoot, ch);
int tempLevel = pPointer->level;     //输入节点(根)所在的层数
maxLevel = tempLevel;
int maxLevel = Ergodic(pPointer); //找到以输入节点为根节点树的,叶子节点所在的最大层数
int level = maxLevel - tempLevel +1;
vec.push_back(level);
test++;
}

return vec;
}

int main()
{

char* input = "a1b2c2d3e4f3g4o4y5h5j6l7";
char* test = "abdeyjfcgohl";
vector<int> vec  = GetLevel(input, test);
cout<<input<<endl<<test<<endl;

for (unsigned int i = 0; i<vec.size(); i++)
{
cout<<vec[i]<<"   ";
}

return 1;
}


 

 

 

=================================================================================

题目:
题目描述(60分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串过滤程序,若字符串中出现多个相同的字符,将非首次出现的字符过滤掉。
比如字符串“abacacde”过滤结果为“abcde”。


要求实现函数:
void stringFilter(const char *pInputStr, long lInputLen, char *pOutputStr);


【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;


【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出


示例
输入:“deefd”        输出:“def”
输入:“afafafaf”     输出:“af”
输入:“pppppppp”     输出:“p”
*/




/*
题目描述(40分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串压缩程序,将字符串中连续出席的重复字母进行压缩,并输出压缩后的字符串。
压缩规则:
1. 仅压缩连续重复出现的字符。比如字符串"abcbc"由于无连续重复字符,压缩后的字符串还是"abcbc".
2. 压缩字段的格式为"字符重复的次数+字符"。例如:字符串"xxxyyyyyyz"压缩后就成为"3x6yz"


要求实现函数:
void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr);


【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;


【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出


示例
输入:“cccddecc”   输出:“3c2de2c”
输入:“adef”     输出:“adef”
输入:“pppppppp” 输出:“8p”


题目描述(50分):
通过键盘输入100以内正整数的加、减运算式,请编写一个程序输出运算结果字符串。
输入字符串的格式为:“操作数1 运算符 操作数2”,“操作数”与“运算符”之间以一个空格隔开。


补充说明:
1. 操作数为正整数,不需要考虑计算结果溢出的情况。
2. 若输入算式格式错误,输出结果为“0”。


要求实现函数:
void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr);


【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;


【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出


示例
输入:“4 + 7”  输出:“11”
输入:“4 - 7”  输出:“-3”
输入:“9 ++ 7”  输出:“0” 注:格式错误


实现:其中第三题写的有些别扭,主要是额外的存储空间,三个函数测试通过了
#include <stdlib.h>
#include <string.h>
//过滤函数
void stringFilter(const char *pInputStr, char *pOutputStr)
{


int a[26] = {0};
const char* pstr = pInputStr;
char* pResult = pOutputStr;
while( *pstr != '\0')
{
a[*pstr - 'a']++;
if(a[*pstr - 'a'] > 1)
{
pstr++;
}
else
{
*pResult = *pstr;
pstr++;
pResult++;
}


}
*pResult = '\0';


}
//压缩字符串
void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr)
{


const char* pFirst = pInputStr;
const char* pSecond = pInputStr+1;
char* pResult = pOutputStr;
int count = 0;
while(*pSecond != '\0')
{
if(*pSecond == *pFirst)
{
count++;
}
else
{
if(count > 0)
{
*pResult++ = count+1 + '0';
}
*pResult++ = *pFirst;
count = 0;
}
pFirst++;
pSecond++;
}
if(count > 0)
{
*pResult++ = count+1 + '0';
}
*pResult++ = *pFirst;
*pResult = '\0';


}


void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr)
{
char* pTemp = (char*)malloc(lInputLen);
char* pLeft = pTemp;
const char* pRight = pInputStr;
while(*pInputStr != '\0')
{
if(*pInputStr == '+' || *pInputStr == '-')
{
pRight = pInputStr + 1;
break;
}
else
{
*pTemp++ = *pInputStr++;
}
}
*pTemp = '\0';
if (pRight == pLeft || *pRight == '+' || *pRight == '-')
{
*pOutputStr++='0';
*pOutputStr = '\0';
return;
}
int L = atoi(pLeft);
int R = atoi(pRight);
int result;
switch (*pInputStr)
{
case '+':
result = L + R;
break;
case '-':
result = L - R;
break;
default:
result = 0;
break;
}
itoa(result, pOutputStr, 10);


}


int main()
{
//char a[] = "youyouare";
//char a1[] = "deefd";
//char a2[] = "afafafaf";
//char a3[] = "ppppp";
//char* b = (char*)malloc(100);
//char* b1 = (char*)malloc(100);
//char* b2 = (char*)malloc(100);
//char* b3 = (char*)malloc(100);
//
//stringFilter(a,b);
//stringFilter(a1,b1);
//stringFilter(a2,b2);
//stringFilter(a3,b3);


//char t1[] = "cccddecc";
//char t2[] = "deefd";
//char t3[] = "pppppp";
//char rt1[15], rt2[15], rt3[15];
//stringZip(t1,0,rt1);
//stringZip(t2,0,rt2);
//stringZip(t3,0,rt3);


char s1[] = "4+7";
char s2[] = "4-7";
char s3[] = "9++7";
char st1[15], st2[15], st3[15];
arithmetic(s1, strlen(s1), st1);
arithmetic(s2, strlen(s2), st2);
arithmetic(s3, strlen(s3), st3);




}

===============================================================

题目描述:  
通过键盘输入任意一个字符串序列,字符串可能包含多个子串,子串以空格分隔。请编写一个程序,自动分离出各个子串,并使用’,’将其分隔,并且在最后也补充一个’,’并将子串存储。 
如果输入“abc def gh i    d”,结果将是abc,def,gh,i,d,  
要求实现函数:  
void DivideString(const char *pInputStr, long lInputLen, char *pOutputStr); 【输入】 pInputStr:  输入字符串 
         lInputLen:  输入字符串长度          
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长; 【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出 
 
示例  
输入:“abc def gh i    d” 输出:“abc,def,gh,i,d,”  
long j = 0; 
for(long i=0;i<lInputLen;i++) { 
  if(pInputStr[i]!=’ ’)    { 
      pOutputStr[j]= pInputStr[i];       j++;    } else { 
   If(pOutputStr[j-1] != ’,’)  { 
   pOutputStr[j]=’,’;    j++;   } }  } 
C_C++_CY_01. 逆序链表输出。 
 
题目描述:  
将输入的一个单向链表,逆序后输出链表中的值。链表定义如下:

typedef struct tagListNode { 
int value; 
struct tagListNode *next; }ListNode; 
 
要求实现函数:  
void converse(ListNode **head); 
【输入】head:    链表头节点,空间已经开辟好 【输出】head:    逆序后的链表头节点 【返回】无 
【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出 
 
示例  
输入:链表  1->2->3->4->5 的头节点head 输出:链表  5->4->3->2->1 的头节点head 

  ListNode *p = new ListNode;   ListNode *q = new ListNode;   ListNode *t = new ListNode;   p = *head;   q = p ->next;   t = NULL;   while(q != NULL)    { 
     t =q->next;      q->next = p;      p = q;      q = t;    } 
   *head = q;    delete p;    delete q;    delete t;   }

 

=========================================================

014华为应届毕业生上机笔试试题(部分)

1、
输入一串字符,只包含“0-10”和“,”找出其中最小的数字和最大的数字(可能不止一个),输出最后剩余数字个数。
如 输入  “3,3,4,5,6,7,7”
   输出   3

2、输入一组身高在170到190之间(5个身高),比较身高差,选出身高差最小的两个身高;若身高差相同,选平均身高高的那两个身高;从小到大输出;
如 输入   170 181 173 186 190
   输出   170 173
3、一组人(n个),围成一圈,从某人开始数到第三个的人出列,再接着从下一个人开始数,最终输出最终出列的人

===========================================================

 

华为2014校招机试样题解析

传送门:http://company.dajie.com/huawei/job/shhf/topic/206711/detail

需进行上机考试的岗位:软件开发工程师、操作系统工程师、底层软件开发工程师、云计算开发工程师、DSP工程师 

在线考试:机考系统的内核为VS2005及JDK1.7,使用Java答题时,类名必须为“Main”;使用C/C++答题时,使用VS2005支持的数据类型和函数。
题目类型:涉及数组、链表、指针、字符串、循环、枚举、排序等等。
考试时长:2小时
考试题目:3道题(共计320分),初级题(60分),中级题(100),高级题(160分),难度递增。
 
各难度上机考试样题
 
初级题:从考试成绩中划出及格线 
10个学生考完期末考试评卷完成后,A老师需要划出及格线,要求如下:
(1) 及格线是10的倍数;
(2) 保证至少有60%的学生及格;
(3) 如果所有的学生都高于60分,则及格线为60分
 
中级题:亮着电灯的盏数
 
一条长廊里依次装有n(1 ≤ n ≤ 65535)盏电灯,从头到尾编号1、2、3、…n-1、n。每盏电灯由一个拉线开关控制。开始,电灯全部关着。
n个学生从长廊穿过。第一个学生把号码凡是1的倍数的电灯的开关拉一下;接着第二个学生把号码凡是2的倍数的电灯的开关拉一下;接着第三个学生把号码凡是3的倍数的电灯的开关拉一下;如此继续下去,最后第n个学生把号码凡是n的倍数的电灯的开关拉一下。n个学生按此规定走完后,长廊里电灯有几盏亮着。
注:电灯数和学生数一致。
 
高级题:地铁换乘
已知2条地铁线路,其中A为环线,B为东西向线路,线路都是双向的。经过的站点名分别如下,两条线交叉的换乘点用T1、T2表示。编写程序,任意输入两个站点名称,输出乘坐地铁最少需要经过的车站数量(含输入的起点和终点,换乘站点只计算一次)。
地铁线A(环线)经过车站:A1 A2 A3 A4 A5 A6 A7 A8 A9 T1 A10 A11 A12 A13 T2 A14 A15 A16 A17 A18

地铁线A(直线)经过车站:B1 B2 B3 B4 B5 T1 B6 B7 B8 B9 B10 T2 B11 B12 B13 B14 B15


第一题

不用算法

第二题(代码已改正,请看代码)

有关的算法:

1.Eratosthenes筛法求素数

2.判断一个数是否为素数

3.说白了,就是求一个整数的所有约数个数

第三题:

有关算法:Floyed求任意两点之间的最短路径,关键在于建图,即如何用邻接矩阵建图


(Eratosthenes筛法给两个链接:

http://blog.pfan.cn/bclz/37462.html

http://hi.baidu.com/yyvszh/item/b074622d20dbbf0f42634a56

判断素数的算法:

http://www.cppblog.com/amazon/archive/2009/06/20/88107.aspx

关于如何求一个自然数的所有约数个数,看这里:

http://wenku.baidu.com/view/9776d5d8ce2f0066f5332270.html

一个不会TLE的代码看这里:

http://hi.baidu.com/neuxxm01/item/d7c914b88bad9543ba0e12db


先把几题的思路写在这里,明天再上具体的代码。To be continued

华为机试一般会给出统一的函数接口,不需要自己写main()函数。这里未给出。

格式请看这里(华为2013机试题):http://blog.csdn.net/arcsinsin/article/details/11017169

PS:今年华为的机试没有给出统一的函数接口,而是自己写好程序,然后submit,和OJ判题是一样的。不过测试数据给得没OJ那么严。

题目共三题,一二两题都很简单,只有第三题稍难(但是也很基础,就是著名的取石子游戏),如果你不知道斐波那契博弈的话。

第三题分析及代码请看这里(9月12号新鲜出炉)http://blog.csdn.net/arcsinsin/article/details/11618517

上代码

第一题:

暴力。分别求出0,10,20,......100作为及格线的通过率,取通过率高于60%且最接近60%的及格线为最终的及格线。

PS:此题数据量小,所以可以暴力。若数据量大,则必须自己写排序。但是在机试时时间宝贵,暴力写起来快,可以为后面的题腾出时间。说实话,这道题就是为小白准备的。

  1. #include<iostream>   
  2. #include<cstdio>   
  3. using namespace std;  
  4.   
  5.   
  6. int main()  
  7. {  
  8.     int a[10];  
  9.     int line[11];  
  10.     double p[11];  
  11.     int res;  
  12.     bool flags = true;  
  13.     for (int i = 0; i < 10; i++)  
  14.     {  
  15.         scanf("%d",&a[i]);  
  16.         if (a[i] < 60) flags = false;  
  17.     }  
  18.     for (int i = 0; i <= 10; i++)  
  19.     {  
  20.         line[i] = 10*i;  
  21.     }  
  22.     for (int i = 0; i <= 10; i++)  
  23.     {  
  24.         int count = 0;  
  25.         for (int j = 0; j < 10; j++)  
  26.         {  
  27.             if (a[j]-line[i] >= 0) count++;  
  28.         }  
  29.         p[i] = count*1.0/10;  
  30.     }  
  31.     double min = 1;  
  32.     double temp;  
  33.     int k;  
  34.     for (int i = 0; i < 10; i++)  
  35.     {  
  36.         temp = p[i] - 0.6;  
  37.         if (temp >= 0 && temp < min)  
  38.         {  
  39.             min = temp;  
  40.             k = i;  
  41.         }  
  42.     }  
  43.     res = line[k];  
  44.     if (flags) res = 60;  
  45.     cout<<res<<endl;  
  46.     system("pause");  
  47.     return 0;  
  48. }  
#include<iostream>
#include<cstdio>
using namespace std;


int main()
{
	int a[10];
	int line[11];
	double p[11];
	int res;
	bool flags = true;
	for (int i = 0; i < 10; i++)
	{
		scanf("%d",&a[i]);
		if (a[i] < 60) flags = false;
	}
	for (int i = 0; i <= 10; i++)
	{
		line[i] = 10*i;
	}
	for (int i = 0; i <= 10; i++)
	{
		int count = 0;
		for (int j = 0; j < 10; j++)
		{
			if (a[j]-line[i] >= 0) count++;
		}
		p[i] = count*1.0/10;
	}
	double min = 1;
	double temp;
	int k;
	for (int i = 0; i < 10; i++)
	{
		temp = p[i] - 0.6;
		if (temp >= 0 && temp < min)
		{
			min = temp;
			k = i;
		}
	}
	res = line[k];
	if (flags) res = 60;
	cout<<res<<endl;
	system("pause");
	return 0;
}


 

第二题:

比较简单的做法,就是直接模拟。

  1. //VS2010环境   
  2. #include "stdafx.h"   
  3. #include<iostream>   
  4. using namespace std;  
  5. bool form[1001];  
  6. int n,count;  
  7. int _tmain(int argc, _TCHAR* argv[])  
  8. {    
  9.     while(cin>>n)  
  10.     {  
  11.         memset(form,1,sizeof(form));  
  12.         count = 0;  
  13.         for(int i=1;i<=n;i++)  
  14.             for(int j=i;j<=n;j++)  
  15.                 if(j%i==0)  
  16.                     form[j]=!form[j];  
  17.         for(int i=1;i<=n;i++)  
  18.             if(form[i]==0)  
  19.                 count++;  
  20.         cout<<"有 "<<count<<" 盏灯是亮着的"<<endl;  
  21.     }  
  22.     system("pause");  
  23.     return 0;  
  24. }  
//VS2010环境
#include "stdafx.h"
#include<iostream>
using namespace std;
bool form[1001];
int n,count;
int _tmain(int argc, _TCHAR* argv[])
{  
	while(cin>>n)
	{
		memset(form,1,sizeof(form));
		count = 0;
		for(int i=1;i<=n;i++)
			for(int j=i;j<=n;j++)
				if(j%i==0)
					form[j]=!form[j];
		for(int i=1;i<=n;i++)
			if(form[i]==0)
				count++;
		cout<<"有 "<<count<<" 盏灯是亮着的"<<endl;
	}
	system("pause");
	return 0;
}

第三题:

  1. #include<iostream>   
  2. #include<cstdio>   
  3. #include<cstring>   
  4. using namespace std;  
  5.   
  6. //Floyed算法求任意两点之间的最短路径,算法复杂度O(n^3)虽然Floyed算法是求最短路径里面算法复杂度最大的算法,但写法简单,用于此处求任意两点之间的最短路合适   
  7. const int inf = 0x3f3f3f3f;//无穷大   
  8. struct Graph  
  9. {  
  10.     char vertex[35][4];  
  11.     int edges[35][35];  
  12.     int visited[35];  
  13. };  
  14. char s1[21][4]={"A1","A2","A3","A4","A5","A6","A7","A8","A9","T1",  
  15.     "A10","A11","A12","A13","T2","A14","A15","A16","A17","A18","A1"};  
  16. char s2[17][4]={"B1","B2","B3","B4","B5","T1","B6","B7","B8","B9",  
  17.     "B10","T2","B11","B12","B13","B14","B15"};  
  18. char v[35][4]={"A1","A2","A3","A4","A5","A6","A7","A8","A9","T1",  
  19.     "A10","A11","A12","A13","T2","A14","A15","A16","A17","A18",  
  20.     "B1","B2","B3","B4","B5","B6","B7","B8","B9","B10","B11",  
  21.     "B12","B13","B14","B15"};  
  22.   
  23. //关键在于如何建图   
  24. void CreateGraph(Graph * &G)  
  25. {  
  26.     int i, j, k;  
  27.     for (i = 0; i < 35; i++)  
  28.     {  
  29.         memcpy(G->vertex[i],v[i],sizeof(v[i]));  
  30.         G->visited[i] = 0;  
  31.     }  
  32.     for (i = 0; i < 35; i++)  
  33.     {  
  34.         for (j = 0; j < 35; j++)  
  35.         {  
  36.             G->edges[i][j] = inf;  
  37.         }  
  38.     }  
  39.     for (k = 0; k < 20; k++)  
  40.     {  
  41.         for (i = 0;strcmp(s1[k],G->vertex[i])!=0; i++);  
  42.         for (j = 0;strcmp(s1[k+1],G->vertex[j])!=0;j++);  
  43.         G->edges[i][j] = 1;  
  44.         G->edges[j][i] = 1;  
  45.     }  
  46.     for (k = 0; k < 16; k++)  
  47.     {  
  48.         for (i = 0;strcmp(s2[k],G->vertex[i])!=0; i++);  
  49.         for (j = 0; strcmp(s2[k+1],G->vertex[j])!=0; j++);  
  50.         G->edges[i][j] = 1;  
  51.         G->edges[j][i] = 1;  
  52.     }  
  53. }  
  54. //Floyed算法求任意两点之间的最短路径   
  55. void Floyed(Graph * &G)  
  56. {  
  57.     int i,j,k;  
  58.     for (k = 0; k < 35; k++)  
  59.     {  
  60.         for (i = 0; i < 35; i++)  
  61.         {  
  62.             for (j = 0; j < 35; j++)  
  63.             {  
  64.                 if (G->edges[i][k] + G->edges[k][j] < G->edges[i][j])  
  65.                 {  
  66.                     G->edges[i][j] = G->edges[i][k] + G->edges[k][j];  
  67.                 }  
  68.             }  
  69.         }  
  70.     }  
  71. }  
  72.   
  73. void ace(Graph *G)  
  74. {  
  75.     char s1[4],s2[4];  
  76.     int i,j;  
  77.     cout<<"请输入起点站与终点站"<<endl;  
  78.     cin>>s1>>s2;  
  79.     for (i = 0;strcmp(s1,G->vertex[i])!=0;i++);  
  80.     for (j = 0;strcmp(s2,G->vertex[j])!=0;j++);  
  81.     cout<<G->edges[i][j]+1<<endl;  
  82. }  
  83. int main()  
  84. {  
  85.     Graph *G = new Graph;  
  86.     CreateGraph(G);  
  87.     Floyed(G);  
  88.     while(1)  
  89.     {  
  90.         ace(G);  
  91.     }  
  92.     system("pause");  
  93.     return 0;  
  94. }  
#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;

//Floyed算法求任意两点之间的最短路径,算法复杂度O(n^3)虽然Floyed算法是求最短路径里面算法复杂度最大的算法,但写法简单,用于此处求任意两点之间的最短路合适
const int inf = 0x3f3f3f3f;//无穷大
struct Graph
{
	char vertex[35][4];
	int edges[35][35];
	int visited[35];
};
char s1[21][4]={"A1","A2","A3","A4","A5","A6","A7","A8","A9","T1",
	"A10","A11","A12","A13","T2","A14","A15","A16","A17","A18","A1"};
char s2[17][4]={"B1","B2","B3","B4","B5","T1","B6","B7","B8","B9",
	"B10","T2","B11","B12","B13","B14","B15"};
char v[35][4]={"A1","A2","A3","A4","A5","A6","A7","A8","A9","T1",
	"A10","A11","A12","A13","T2","A14","A15","A16","A17","A18",
	"B1","B2","B3","B4","B5","B6","B7","B8","B9","B10","B11",
	"B12","B13","B14","B15"};

//关键在于如何建图
void CreateGraph(Graph * &G)
{
	int i, j, k;
	for (i = 0; i < 35; i++)
	{
		memcpy(G->vertex[i],v[i],sizeof(v[i]));
		G->visited[i] = 0;
	}
	for (i = 0; i < 35; i++)
	{
		for (j = 0; j < 35; j++)
		{
			G->edges[i][j] = inf;
		}
	}
	for (k = 0; k < 20; k++)
	{
		for (i = 0;strcmp(s1[k],G->vertex[i])!=0; i++);
		for (j = 0;strcmp(s1[k+1],G->vertex[j])!=0;j++);
		G->edges[i][j] = 1;
		G->edges[j][i] = 1;
	}
	for (k = 0; k < 16; k++)
	{
		for (i = 0;strcmp(s2[k],G->vertex[i])!=0; i++);
		for (j = 0; strcmp(s2[k+1],G->vertex[j])!=0; j++);
		G->edges[i][j] = 1;
		G->edges[j][i] = 1;
	}
}
//Floyed算法求任意两点之间的最短路径
void Floyed(Graph * &G)
{
	int i,j,k;
	for (k = 0; k < 35; k++)
	{
		for (i = 0; i < 35; i++)
		{
			for (j = 0; j < 35; j++)
			{
				if (G->edges[i][k] + G->edges[k][j] < G->edges[i][j])
				{
					G->edges[i][j] = G->edges[i][k] + G->edges[k][j];
				}
			}
		}
	}
}

void ace(Graph *G)
{
	char s1[4],s2[4];
	int i,j;
	cout<<"请输入起点站与终点站"<<endl;
	cin>>s1>>s2;
	for (i = 0;strcmp(s1,G->vertex[i])!=0;i++);
	for (j = 0;strcmp(s2,G->vertex[j])!=0;j++);
	cout<<G->edges[i][j]+1<<endl;
}
int main()
{
	Graph *G = new Graph;
	CreateGraph(G);
	Floyed(G);
	while(1)
	{
		ace(G);
	}
	system("pause");
	return 0;
}


以上定有不足之处,还请多多指教。

 

=====================================

2014华为校园招聘机试——字符串过滤、压缩等

分类: java 2124人阅读 评论(7) 收藏 举报

看了很多博客,发现今年去华为机试的人,同一批的题目大多都是相同的,不同批次的题目大多不相同。当然,这些题目可能在以前出现过,去年,或者前年等。所以,多看一下不同人的题目,对自己是有好处的!

说一下机试的打分情况。机试的打分是通过测试用例的成功数量来给分的,每个用例20分,一共16个用例(共三道题,共320分=60(题一)+100(题二)+160(题三)),通过一个用例,给20分,通过两个,给40分,以此类推。所以答题时一定要注意边界条件,考虑周全。

以下是一位机试者的题目,是用c实现的,我用JAVA重写了一遍,并发现他的程序有几个问题

题一:题目描述(60分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串过滤程序,若字符串中出现多个相同的字符,将非首次出现的字符过滤掉。
比如字符串“abacacde”过滤结果为“abcde”。
要求实现函数: 
void stringFilter(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“deefd”        输出:“def”
输入:“afafafaf”     输出:“af”
输入:“pppppppp”     输出:“p”

题二:题目描述(40分):
通过键盘输入一串小写字母(a~z)组成的字符串。请编写一个字符串压缩程序,将字符串中连续出席的重复字母进行压缩,并输出压缩后的字符串。
压缩规则:
1. 仅压缩连续重复出现的字符。比如字符串"abcbc"由于无连续重复字符,压缩后的字符串还是"abcbc".
2. 压缩字段的格式为"字符重复的次数+字符"。例如:字符串"xxxyyyyyyz"压缩后就成为"3x6yz"

要求实现函数: 
void stringZip(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“cccddecc”   输出:“3c2de2c”
输入:“adef”     输出:“adef”
输入:“pppppppp” 输出:“8p”
 

题三:题目描述(50分): 
通过键盘输入100以内正整数的加、减运算式,请编写一个程序输出运算结果字符串。
输入字符串的格式为:“操作数1 运算符 操作数2”,“操作数”与“运算符”之间以一个空格隔开。

补充说明:
1. 操作数为正整数,不需要考虑计算结果溢出的情况。
2. 若输入算式格式错误,输出结果为“0”。

要求实现函数: 
void arithmetic(const char *pInputStr, long lInputLen, char *pOutputStr);

【输入】 pInputStr:  输入字符串
         lInputLen:  输入字符串长度         
【输出】 pOutputStr: 输出字符串,空间已经开辟好,与输入字符串等长;

【注意】只需要完成该函数功能算法,中间不需要有任何IO的输入输出

示例 
输入:“4 + 7”  输出:“11”
输入:“4 - 7”  输出:“-3”
输入:“9 ++ 7”  输出:“0” 注:格式错误

题一:

  1. public class Test4_1 {  
  2.     private static void stringFilter(char[] inputStr,long length,char[] outputStr){  
  3.         int[] a=new int[26];  
  4.         int len=0;        
  5.         for(int i=0;i<length;i++){  
  6.             int temp=0;  
  7.             temp=inputStr[i]-'a';  
  8.             if(a[temp]==0){  
  9.                 outputStr[len++]=inputStr[i];  
  10.                 a[temp]=1;  
  11.             }else{  
  12.                 continue;  
  13.             }  
  14.         }  
  15.     }  
  16.       
  17.     public static void main(String[] args){  
  18.         char[] inputStr=new char[]{'d','e','e','f','d','e','p'};  
  19.         long n=inputStr.length;  
  20.         char[] outputStr=new char[(int)n];  
  21.         stringFilter(inputStr,n,outputStr);  
  22.         for(int i=0;i<n;i++){  
  23.             System.out.print(outputStr[i]);  
  24.         }  
  25.     }  
public class Test4_1 {
	private static void stringFilter(char[] inputStr,long length,char[] outputStr){
		int[] a=new int[26];
		int len=0;		
		for(int i=0;i<length;i++){
			int temp=0;
			temp=inputStr[i]-'a';
			if(a[temp]==0){
				outputStr[len++]=inputStr[i];
				a[temp]=1;
			}else{
				continue;
			}
		}
	}
	
	public static void main(String[] args){
		char[] inputStr=new char[]{'d','e','e','f','d','e','p'};
		long n=inputStr.length;
		char[] outputStr=new char[(int)n];
		stringFilter(inputStr,n,outputStr);
		for(int i=0;i<n;i++){
			System.out.print(outputStr[i]);
		}
	}

输出:defp

题二:

  1. public class Test3 {  
  2.     private static void stringZip(char[] inputStr,long length,char[] outputStr){  
  3.         int i=0;  
  4.         int len=0;        
  5.         while(i<length){  
  6.             int time=1;  
  7.             char c=inputStr[i++];         
  8.             while(i<length&&c==inputStr[i]){  
  9.                 time++;  
  10.                 i++;  
  11.             }  
  12.             if(time==1){  
  13.                 outputStr[len++]=c;  
  14.             }else if(time<=9){  
  15.                 outputStr[len++]=(char)(time+'0');  
  16.                 outputStr[len++]=c;  
  17.             }else if(time<=99){                
  18.                 outputStr[len++]=(char)(time/10+'0');  
  19.                 outputStr[len++]=(char)(time%10+'0');  
  20.                 outputStr[len++]=c;               
  21.             }else{  
  22.                 //当连续重复的字符数超过99时,用一个“?”来表示。   
  23.                 outputStr[len++]=(char)63;  
  24.                 outputStr[len++]=c;  
  25.             }  
  26.         }         
  27.     }     
  28.     public static void main(String[] args){  
  29.         char[] inputStr=new char[]{'c','a','a','f','f','f','f','f','f','f','f','f','f','f','f'};  
  30.         long length=inputStr.length;  
  31.         char[] outputStr=new char[(int)length];  
  32.         stringZip(inputStr,length,outputStr);  
  33.         for(int i=0;i<outputStr.length;i++){  
  34.             System.out.print(outputStr[i]);  
  35.         }  
  36.     }  
  37. }  
public class Test3 {
	private static void stringZip(char[] inputStr,long length,char[] outputStr){
		int i=0;
		int len=0;		
		while(i<length){
			int time=1;
			char c=inputStr[i++];		
			while(i<length&&c==inputStr[i]){
				time++;
				i++;
			}
			if(time==1){
				outputStr[len++]=c;
			}else if(time<=9){
				outputStr[len++]=(char)(time+'0');
				outputStr[len++]=c;
			}else if(time<=99){				
				outputStr[len++]=(char)(time/10+'0');
				outputStr[len++]=(char)(time%10+'0');
				outputStr[len++]=c;				
			}else{
				//当连续重复的字符数超过99时,用一个“?”来表示。
				outputStr[len++]=(char)63;
				outputStr[len++]=c;
			}
		}		
	}	
	public static void main(String[] args){
		char[] inputStr=new char[]{'c','a','a','f','f','f','f','f','f','f','f','f','f','f','f'};
		long length=inputStr.length;
		char[] outputStr=new char[(int)length];
		stringZip(inputStr,length,outputStr);
		for(int i=0;i<outputStr.length;i++){
			System.out.print(outputStr[i]);
		}
	}
}

输出:c2a12f

题三:

  1. public class Test4_2 {  
  2.     private static void arithmetic(char[] inputStr,long length,char[] outputStr){  
  3.         int num1=0;  
  4.         int num2=0;  
  5.         boolean first=true;  
  6.         boolean oper=false;  
  7.         boolean zero=false;  
  8.         int once=0;  
  9.           
  10.         for(int i=0;i<length;i++){  
  11.             if(inputStr[i]==' '){  
  12.                 continue;                 
  13.             }  
  14.             if(inputStr[i]>='0'&&inputStr[i]<='9'){  
  15.                 if(first){  
  16.                     num1=num1*10+inputStr[i]-'0';  
  17.                       
  18.                 }else{  
  19.                     num2=num2*10+inputStr[i]-'0';  
  20.                 }  
  21.             }else{  
  22.                   
  23.                 if(once==0){  
  24.                     if(inputStr[i]=='-'){  
  25.                         oper=false;  
  26.                         once=1;  
  27.                     }else{  
  28.                         oper=true;  
  29.                         once=1;  
  30.                     }  
  31.                     first=false;  
  32.                 }else{  
  33.                     zero=true;  
  34.                     break;  
  35.                 }                 
  36.             }  
  37.         }  
  38.           
  39.         if(zero){  
  40.             outputStr[0]='0';             
  41.         }else{  
  42.             int sum=0;  
  43.             if(oper){  
  44.                 sum=num1+num2;  
  45.             }else{  
  46.                 sum=num1-num2;  
  47.             }  
  48.             int i=0;  
  49.             if(sum<0){  
  50.                 outputStr[i++]='-';  
  51.                 sum=0-sum;  
  52.             }  
  53.               
  54.             if(sum>=0&&sum<=9){  
  55.                 outputStr[i++]=(char)(sum+'0');  
  56.             }else if(sum>9&&sum<=99){  
  57.                 int tmp=sum/10;  
  58.                 outputStr[i++]=(char)(tmp+'0');  
  59.                 sum=sum%10;  
  60.                 outputStr[i++]=(char)(sum+'0');  
  61.             }else if(sum>99){  
  62.                 int tmp=sum/100;  
  63.                 outputStr[i++]=(char)(tmp+'0');  
  64.                 sum=sum%100;  
  65.                 tmp=sum/10;  
  66.                 outputStr[i++]=(char)(tmp+'0');  
  67.                 sum=sum%10;  
  68.                 outputStr[i++]=(char)(sum+'0');               
  69.             }     
  70.               
  71.         }  
  72.     }  
  73.       
  74.     public static void main(String[] args){  
  75.         char[] inputStr=new char[]{'4',' ','-',' ','7'};  
  76.         long n=inputStr.length;  
  77.         char[] outputStr=new char[(int)n];  
  78.         arithmetic(inputStr,n,outputStr);  
  79.         for(int i=0;i<outputStr.length;i++){  
  80.             System.out.print(outputStr[i]);  
  81.         }  
  82.     }  
  83. }  
public class Test4_2 {
	private static void arithmetic(char[] inputStr,long length,char[] outputStr){
		int num1=0;
		int num2=0;
		boolean first=true;
		boolean oper=false;
		boolean zero=false;
		int once=0;
		
		for(int i=0;i<length;i++){
			if(inputStr[i]==' '){
				continue;				
			}
			if(inputStr[i]>='0'&&inputStr[i]<='9'){
				if(first){
					num1=num1*10+inputStr[i]-'0';
					
				}else{
					num2=num2*10+inputStr[i]-'0';
				}
			}else{
				
				if(once==0){
					if(inputStr[i]=='-'){
						oper=false;
						once=1;
					}else{
						oper=true;
						once=1;
					}
					first=false;
				}else{
					zero=true;
					break;
				}				
			}
		}
		
		if(zero){
			outputStr[0]='0';			
		}else{
			int sum=0;
			if(oper){
				sum=num1+num2;
			}else{
				sum=num1-num2;
			}
			int i=0;
			if(sum<0){
				outputStr[i++]='-';
				sum=0-sum;
			}
			
			if(sum>=0&&sum<=9){
				outputStr[i++]=(char)(sum+'0');
			}else if(sum>9&&sum<=99){
				int tmp=sum/10;
				outputStr[i++]=(char)(tmp+'0');
				sum=sum%10;
				outputStr[i++]=(char)(sum+'0');
			}else if(sum>99){
				int tmp=sum/100;
				outputStr[i++]=(char)(tmp+'0');
				sum=sum%100;
				tmp=sum/10;
				outputStr[i++]=(char)(tmp+'0');
				sum=sum%10;
				outputStr[i++]=(char)(sum+'0');				
			}	
			
		}
	}
	
	public static void main(String[] args){
		char[] inputStr=new char[]{'4',' ','-',' ','7'};
		long n=inputStr.length;
		char[] outputStr=new char[(int)n];
		arithmetic(inputStr,n,outputStr);
		for(int i=0;i<outputStr.length;i++){
			System.out.print(outputStr[i]);
		}
	}
}

输出:-3

===================================================

2013华为校园招聘上机题——约瑟夫环

输入一个由随机数组成的数列(数列中每个数均是大于0的整数,长度已知),和初始计数值m。从数列首位置
开始计数,计数到m后,将数列该位置数值替换计数值m,并将数列该位置数值出列,然后从下一位置从新开始
计数,直到数列所有数值出列为止。如果计数到达数列尾段,则返回数列首位置继续计数。
请编程实现上述计数过程,同时输出数值出列的顺序。
 
这道题不难,但发现很多人给出的答案中的数列不是随机生成的,现在加上随机生成的数列的约瑟夫环的实现过程。
  1. packagehuawei;  
  2.    
  3. importjava.util.LinkedList;  
  4. importjava.util.Random;  
  5.    
  6. publicclassTest6_1 {  
  7.     privatestaticintscanPeople(String s) {  
  8.                //用链表来实现“约瑟夫环”是一种很好的方式,可以方便的动态插入、删除、移动等。   
  9.         LinkedList<Integer> plist=newLinkedList<Integer>();  
  10.         try{  
  11.             intn=Integer.parseInt(s);                 
  12.             intstart=1;  
  13.             intend=20;  
  14.             Random rand=newRandom();  
  15.             for(inti=0;i<n;i++){  
  16.                  //由于题目要求“数列中每个数均是大于0的整数”,而系统提供的Random是从0开始的,   
  17. //故自己写一个任意的范围可控的函数showRandom,如下:   
  18.                 intj=showRandom(start,end,rand);  
  19.                 plist.add(j);  
  20.                 System.out.print(j+" ");                 
  21.             }  
  22.             System.out.println("***");  
  23.             intcirclecount=0;  
  24.             while(plist.size()>1){  
  25.                 for(inti=0;i<plist.size();i++){  
  26.                     circlecount++;  
  27.                                         //这里的m=3,且m是可以随意设置的   
  28.                     if(circlecount==3){  
  29.                         plist.remove(i);  
  30.                                    //删除了一个元素,后面的元素会整体前移一个单位,故减一   
  31.                         i--;  
  32.                         circlecount=0;  
  33.                     }  
  34.                 }  
  35.             }               
  36.             returnplist.get(0);  
  37.         }catch(NumberFormatException e){  
  38.             return0;  
  39.         }           
  40.     }  
  41.        
  42.     privatestaticintshowRandom(intstart,intend,Random rand){  
  43.         if(start>end){  
  44.             thrownewIllegalArgumentException("start cannot exceed end");  
  45.         }  
  46.         longrange=(long)(end-start+1);  
  47.         longfraction=(long)(range*rand.nextDouble());  
  48.         intsum=(int)(start+fraction);  
  49.         returnsum;  
  50.     }  
  51.        
  52.     publicstaticvoidmain(String[] args){  
  53.         System.out.println(scanPeople("12"));  
  54.         System.out.println(scanPeople("11a"));  
  55.            
  56.     }  
  57.    
  58. }  
packagehuawei;
 
importjava.util.LinkedList;
importjava.util.Random;
 
publicclassTest6_1 {
    privatestaticintscanPeople(String s) {
               //用链表来实现“约瑟夫环”是一种很好的方式,可以方便的动态插入、删除、移动等。
        LinkedList<Integer> plist=newLinkedList<Integer>();
        try{
            intn=Integer.parseInt(s);               
            intstart=1;
            intend=20;
            Random rand=newRandom();
            for(inti=0;i<n;i++){
                 //由于题目要求“数列中每个数均是大于0的整数”,而系统提供的Random是从0开始的,
//故自己写一个任意的范围可控的函数showRandom,如下:
                intj=showRandom(start,end,rand);
                plist.add(j);
                System.out.print(j+" ");               
            }
            System.out.println("***");
            intcirclecount=0;
            while(plist.size()>1){
                for(inti=0;i<plist.size();i++){
                    circlecount++;
                                        //这里的m=3,且m是可以随意设置的
                    if(circlecount==3){
                        plist.remove(i);
                                   //删除了一个元素,后面的元素会整体前移一个单位,故减一
                        i--;
                        circlecount=0;
                    }
                }
            }             
            returnplist.get(0);
        }catch(NumberFormatException e){
            return0;
        }         
    }
     
    privatestaticintshowRandom(intstart,intend,Random rand){
        if(start>end){
            thrownewIllegalArgumentException("start cannot exceed end");
        }
        longrange=(long)(end-start+1);
        longfraction=(long)(range*rand.nextDouble());
        intsum=(int)(start+fraction);
        returnsum;
    }
     
    publicstaticvoidmain(String[] args){
        System.out.println(scanPeople("12"));
        System.out.println(scanPeople("11a"));
         
    }
 
}


     http://www.javapractices.com/topic/TopicAction.do?Id=62

 

=========================

 

华为机试有一道“鉴定回文数”的题,看了一些文章,不管是用数组实现,还是用字符串实现,代码都太多,太麻烦。

本人用java的字符串,只需几行代码,轻松搞定。

  1. public class IsSymmetry {  
  2.     //对比其他方法,你会发现函数symmetry的代码行数很少。   
  3.     private static String symmetry(long data){  
  4.         String s=data+"";  
  5.         for(int i=0;i<s.length()/2;i++){  
  6.             if(s.charAt(i)!=s.charAt(s.length()-1-i)){  
  7.                 return "No";  
  8.             }  
  9.         }  
  10.         return "Yes";  
  11.     }     
  12.       
  13.     public static void main(String[] args){  
  14.         long n1=1436341;  
  15.         long n2=1234565;          
  16.         System.out.println(n1+"是回文数吗?"+symmetry(n1));  
  17.         System.out.println(n2+"是回文数吗?"+symmetry(n2));  
  18.     }  
  19. }  
public class IsSymmetry {
	//对比其他方法,你会发现函数symmetry的代码行数很少。
	private static String symmetry(long data){
		String s=data+"";
		for(int i=0;i<s.length()/2;i++){
			if(s.charAt(i)!=s.charAt(s.length()-1-i)){
				return "No";
			}
		}
		return "Yes";
	}	
	
	public static void main(String[] args){
		long n1=1436341;
		long n2=1234565;		
		System.out.println(n1+"是回文数吗?"+symmetry(n1));
		System.out.println(n2+"是回文数吗?"+symmetry(n2));
	}
}


 

输出:1436341是回文数吗?Yes

            1234565是回文数吗?No

=====

今天华为面试失败,来这里吐槽,发发牢骚,缓解一下情绪。感悟几点如下:

1.面试时间很长。昨晚收到面试通知,今早就提前赶到华为,9:40签到,10点的时候叫到我,被面试官带到一个很多的大厅里面,那里有很多人在面试,一对一,而不是群面(当时感觉蛮不错的,这至少说明华为尊重每一位应聘者)。这第一面是技术面,从我之前面试回来的同学那里知道他们大多在40分钟左右,最快20分钟搞定的都有,而我的面试从10点整开始,一直到11点整才结束,足足一个小时。当时觉得面这么久,进去的可能性很大,可快结束的时候,他跟我说了一句,“我这面就不过了”。一听到这句话,顿时头脑一片空白,持续了好久秒钟。所以,面得久也不一定就好。

2.技术问题。第一个问题,他问了折半插入排序的时间复杂度,我答出来了,O(nlogn)。他让我用旁边的笔和纸演示一下是如何插入的,我详细的演示了一遍。他问这个复杂度是怎么算的,我也分析了n和logn。他最后让我详细的演示一下去掉O的时间复杂度的过程,我说忘了。他就没在继续往下问,这里虽然有点问题,但自我感觉还可以。第二个问题,他问了hashTable和hashMap的区别,我说有7个区别,准备一一列出,刚说完第二个,他就说那是书上的,用你自己的话说。我马上说了同步这一点。他暗示这点是对的,但不全,接着听他补充了一些。

3.兴趣问题。由于跟导师做过天线,而现在面试的岗位是“软件研发”,他就说,“智能天线的前途非常好,问我为何从事软件行业“,我说了一大堆自己开始对软件感兴趣,并想往这边深入进去的事。他就说我太乐观,并强调”码农的工作很枯燥的,和其他行业的工人没什么区别“。在交谈了一段时间之后,他说,”如果你做这个3年之后,感到没兴趣了,你就会离开,华为新员工工作3年左右的离职率在50%左右“,停顿了一会儿,他接着说道,”兴趣什么都不是“。听到这句话时,心有点凉了。感觉这位在华为工作了13年(他自己说的)的员工在感慨程序员生活枯燥、不乐观的同时,也失去了对美好程序人生的憧憬和向往。让我顿时想起了一句话,”经验会阻碍你前进的步伐“。

4.java VS c++。由于我面的是java,他就说java的是偏应用层的,很多库类已经被封装起来,直接调用就是,这里没有太多作为,没有太大吸引力。所以短时间内上手之后,就是不断的重复性的工作。问我到时没兴趣了之后怎么办,我说可以往底层发展,做后端开发。他说:”从后端到前端易,从前端到后端难啊“。”相信我,兴趣能让我克服这些困难的“,我接着说道。他笑了笑,从他的相声中,我听到了”鄙视“。聊了一下之后,他说我没有C++方面的经验,想做底层开发,应该学c++,同时看一些算法和数据结构的书。

5.面试官。说实话,他还是蛮和善的,整个过程都比较轻松,没有给我压力和其他不良的信号。他给我一些建议也是比较中肯的,谢谢!

 

 

展开阅读全文

没有更多推荐了,返回首页