zoukankan      html  css  js  c++  java
  • 面试题目——《CC150》中等难题

    面试题17.1:编写一个函数,不用临时变量,直接交换两个数。

      思路:使用差值或者异或

    package cc150.middle;
    
    public class Exchange {
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    		int[] a= {1,2};
    		Exchange ec = new Exchange();
    		int[] b= ec.exchangeAB(a);
    		System.out.println(b[0]);
    		System.out.println(b[1]);
    	}
    	
    	 public int[] exchangeAB(int[] AB) {
    	        // write code here
    //		 	AB[0] = AB[0]-AB[1];
    //		 	AB[1] = AB[0]+AB[1]; 
    //		 	AB[0] = AB[1]-AB[0]; 
    		 
    		 	AB[0] = AB[0]^AB[1];
    		 	AB[1] = AB[0]^AB[1]; 
    		 	AB[0] = AB[1]^AB[0]; 
    		 	return AB;
    	    }
    
    }
    

    面试题17.2:设计一个算法,判断玩家是否赢了井字游戏。

    package cc150.middle;
    
    public class Board {	//井字棋
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    		int[][] a = {{1,0,1},{1,-1,-1},{1,-1,0}};
    		Board b = new Board();
    		System.out.println(b.checkWon(a));
    	}
    	
    	public boolean checkWon(int[][] board) {
            // write code here
    		int N = board.length;
    		int row = 0;
    		int col = 0;
    		
    		//检查行
    		for(row = 0;row<N;row++){
    			for(col = 1;col<N;col++){
    				if(board[row][col] != board[row][col-1])
    					break;
    			}
    			if(col == N && board[row][col-1] == 1)
    				return true;
    		}
    		
    		//检查列
    		for(col = 0;col<N;col++){
    			for(row = 1;row<N;row++){
    				if(board[row][col] != board[row-1][col])
    					break;
    			}
    			if(row == N && board[row-1][col] == 1)
    				return true;
    		}
    		
    		//检查对角线,从左上角开始
    		if(board[0][0] != 0){
    			for(row = 1;row<N;row++){
    				if(board[row][row] != board[row-1][row-1])
    					break;
    			}
    			if(row == N && board[row-1][row-1] == 1)
    				return true;
    		}
    		
    		//检查对角线,左下角开始
    		if(board[N-1][0] != 0){
    			for(row = 1;row<N;row++){
    				if(board[N-row-1][row] != board[N-row][row-1])
    					break;
    			}
    			if(row == N && board[N-row][row-1] == 1)
    				return true;
    		}
    		return false;
        }
    
    }
    

    面试题17.3:设计一个算法,算出n阶乘有多少个尾随零。

    package cc150.middle;
    
    public class Factor {
    
    	public static void main(String[] args) {		//n阶乘有多少个尾随零
    		// TODO 自动生成的方法存根
    		Factor f = new Factor();
    		System.out.println(f.getFactorSuffixZero(10));
    	}
    	
    	public int getFactorSuffixZero(int n) {//统计所有相乘的数中分解出5的个数,2的个数必定大于5,只要统计5的个数即可
            // write code here
    //		int count = 0;
    //		for(int i=2;i<=n;i++)
    //			count += factorOf5(i);
    //		return count;
    		
    		int count = 0;
    		for(int i=5;n/i>0;i*=5)		//如果n=10的话,有2个数在5和25之间
    			count += n/i;
    		return count;
        }
    	
    	public int factorOf5(int n) {
            // write code here
    		int count = 0;
    		while(n%5 == 0){	//求余数
    			count ++;
    			n/=5;
    		}
    		return count;
        }
    
    }
    

    面试题17.4:编写一个方法,找出两个数字中最大的那一个。不得使用if-else或其他比较运算符。

    package cc150.middle;
    
    public class Max {
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    		
    	}
    	
    	public int getMax(int a, int b) {
            // write code here
    		b = a-b;					//此时b>>31为1则b小于0即a<b,若b>>31为0 则a>b
    	    a -= b&(b>>31); 	//若a<b a=a-(a-b),若a>b a=a-0 
    	    return a;
        }
    
    }
    

    面试题17.6:给定一个整数数组,编写一个函数,找出索引m和n,只要将m和n之间的元素排好序,整个数组就是有序的。注意:n-m越小越好,也就是说,找出符合条件的最短序列。

    面试题17.7:给定一个整数,打印该整数的英文描述(例如“One Thousand,Two Hundred Thirty Four”)。

    package cc150.middle;
    
    public class ToString {
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    		ToString ts = new ToString();
    		System.out.println(ts.toString(1000));		//输入1234,输出"One Thousand,Two Hundred Thirty Four"
    	}
    	
    	public static String[] digits = {"One","Two","Three","Four","Five","Six","Seven","Eight","Nine"};
    	public static String[] teens = {"Eleven","Twelve","Thirteen","Fourteen","Fifteen","Sixteen","Seventeen","Eighteen","Nineteen"};
    	public static String[] tens = {"Ten","Twenty","Thirty","Forty","Fifty","Sixty","Seventy","Eighty","Ninety"};
    	public static String[] bigs = {"","Thousand","Million"};
    	
    	public String toString(int x) {
            // write code here
    		if(x == 0)
    			return "Zero";
    		else if(x < 0)
    			return "Negative " + toString(-1*x);
    		int count = 0;
    		String str = "";
    		while(x > 0){
    			if(x % 1000 != 0){		
    				if(count == 0 || str == "")  //One Million后面不能有逗号
    					str = toString100(x % 1000)+bigs[count]+str; //把count大的million放在前面,原来的str放在后面
    				else
    					str = toString100(x % 1000)+bigs[count]+","+str; //把count大的million放在前面,原来的str放在后面
    			}
    			x /= 1000;
    			count ++;
    		}
    		return str.trim();
        }
    	
    	public String toString100(int x){
    		String str = "";
    		//转换百位数的地方
    		if(x >= 100){
    			str+=digits[x/100-1]+" Hundred ";
    			x%=100;
    		}
    		//转换十位数的地方
    		if(x >= 11 && x <= 19){
    			return str+teens[x-11]+" ";
    		}else if(x == 10 || x >= 20){
    			str+=tens[x/10-1]+" ";
    			x%=10;
    		}
    		//转换个位数的地方
    		if(x >= 1 && x<=9){
    			str+=digits[x-1]+" ";		
    		}
    		return str;
    	}
    	
    	
    
    }
    

    面试题17.8:给定一个整数数组(有正数有负数),找出总和最大的连续数列,并返回总和。(剑指Offer原题)

    package jianzhiOffer;
    
    public class FindGreatestSumOfSubArray {		//连续子数组的最大和
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    //		int[] Arr = {-1,-2,-3,-10,-4,-7,-2,-5};
    		int[] Arr = {6,-3,-2,7,-15,1,2,2};
    		System.out.println(findGreatestSumOfSubArray(Arr));
    	}
    	
    	public static boolean InvalidInput = false;
    	
    	public static int findGreatestSumOfSubArray(int[] nums){
    		if(nums == null || nums.length<=0){
    			InvalidInput = true;
    			return 0;
    		}
    		InvalidInput = true;
    		int curSum = 0;
    		int curGreatestSum = Integer.MIN_VALUE;//数组内可能全部都是负数
    		for(int i=0;i<nums.length;i++){
    			if(curSum < 0)//如果前n个相加小于0,那么最大的和只能从n+1个开始算
    				curSum = nums[i];
    			else
    				curSum += nums[i];
    			if(curSum > curGreatestSum)//数组内可能全部都是负数
    				curGreatestSum = curSum;
    		}
    		return curGreatestSum;
    	}
    
    }
    

    面试题17.9:设计一个方法,找出任意指定单词在一本书中的出现频率。

    package cc150.middle;
    
    import java.util.Hashtable;
    
    public class Frequency {
    
    	public static void main(String[] args) {
    		// TODO 自动生成的方法存根
    		
    	}
    	
    	public int getFrequency(String[] article, int n, String word) {
            // write code here
    		return wordFrequency(setupDictionary(article),word);
        }
    	
    	public Hashtable<String,Integer> setupDictionary(String[] book){
    		Hashtable<String,Integer> table = new Hashtable<String,Integer>();
    		for(String word:book){
    			word = word.toLowerCase();
    			if(word.trim() != ""){		//去掉空格之后,不等于空
    				if(!table.containsKey(word))
    					table.put(word, 0);
    				table.put(word, table.get(word)+1);
    			}
    		}
    		return table;
    	}
    	
    	public int wordFrequency(Hashtable<String,Integer> table, String word){
    		if(table == null || word == null)
    			return -1;
    		word = word.toLowerCase();
    		if(table.containsKey(word))
    			return table.get(word);
    		return 0;
    	}
    
    }
    

    面试题17.12:设计一个算法,找出数组中两数之和为指定值的所有整数对。

    package cc150.middle;
    
    import java.util.Arrays;
    
    public class FindPair {
    
    	public static void main(String[] args) {		//有重复的情况
    		// TODO 自动生成的方法存根
    		int[] a = {11,7,7,6,14,2,14,15,2,1,2,12,13,9,8,15,13,8,10,11,14,10,2,9,4,9,3,7,6,10,15,4,7,6,15,3,9,13,5,2,6,10,10,1,12,4,3,3,8,8,1,4,7,11,13,5,13,15,4,3,1,11,6,11,9,9,11,15,12,10,13,3,11,4,8,9,7,3,13,9,11,3,2,11,10,1,4,2,3,3,14,11,5,10,1,14,8,1,11,3,1,9,14,6,1,7,15,10,14,6,4,12,11};
    		FindPair fp = new FindPair();
    		System.out.println(fp.countPairs(a,113,16));
    	}
    	
    	public int countPairs(int[] A, int n, int sum) {
            // write code here
    		Arrays.sort(A);
    		for(int i=0;i<A.length;i++)
    			System.out.println(A[i]);
    		int first = 0;
    		int end = n-1;
    		int count=0;
    		int countLeft = 1;
    		int countRight = 1;
    		while(first<end){
    			int s = A[first]+A[end];
    			if(s == sum){							//如果相等
    				if(A[first] == A[end]){		//情况1,一串连续的,且这些相加等于sum
    					count += ((end-first)*(end-first+1)/2);
    					return count;		//注意要在这里结束,否则会继续计数
    				}else{									//情况2,两串连续的,两个串中各取一个相加等于sum
    					while(A[first] == A[first+1]){
    						countLeft++;
    						first++;
    					}
    					while(A[end] == A[end-1]){
    						countRight++;
    						end--;
    					}
    					count += (countLeft*countRight);
    				}
    				first++;
    				end--;
    				countLeft=1;		//注意开始计数是1
    				countRight=1;
    			}else{
    				if(s>sum)
    					end--;
    				else
    					first++;
    			}
    		}
    		return count;
        }
    
    }
    

    面试题17.13:有个简单的类似结点的数据结构BiNode,包含两个指向其他结点的指针。数据结构BiNode可用来表示二叉树(其中node1为左子节点,node2为右子节点)或双向链表(其中node1为前趋结点,node2为后继结点)。编写一个方法,将二叉查找树(用BiNode实现)转换为双向链表。要求所有数值的排序不变,转换操作不得引入其他数据结构(即直接操作原先的数据结构)。

    package cc150.middle;
    
    public class Converter {
    
    	public static void main(String[] args) {		//二叉查找树转换成双向链表
    		// TODO 自动生成的方法存根
    		Converter cv = new Converter();
    		TreeNode t4 = cv.new TreeNode(4);
    		TreeNode t2 = cv.new TreeNode(2);
    		TreeNode t5 = cv.new TreeNode(5);
    		TreeNode t1 = cv.new TreeNode(1);
    		TreeNode t3 = cv.new TreeNode(3);
    		TreeNode t6 = cv.new TreeNode(6);
    		TreeNode t0 = cv.new TreeNode(0);
    		t4.left = t2;
    		t4.right = t5;
    		t2.left = t1;
    		t2.right = t3;
    		t5.right = t6;
    		t1.left = t0;
    		cv.treeToList(t4);
    		while(cv.head.next != null){
    			System.out.println(cv.head.val);
    			cv.head = cv.head.next;
    		}
    			
    	}
    	
    	private ListNode head  = new ListNode(-1);
    	private ListNode q  = head;
    	
    	public ListNode treeToList(TreeNode root) {		//使用中序遍历
            // write code here
    		if(root != null){
    			treeToList(root.left);
    			q.next = new ListNode(root.val);
    			q = q.next;
    			treeToList(root.right);
    		}
    		return head.next;
    		
        }
    	
    	public class ListNode {
    	    int val;
    	    ListNode next = null;
    
    	    ListNode(int val) {
    	        this.val = val;
    	    }
    	}
    	
    	public class TreeNode {
    	    int val = 0;
    	    TreeNode left = null;
    	    TreeNode right = null;
    	    public TreeNode(int val) {
    	        this.val = val;
    	    }
    	}
    	
    	
    }
    
  • 相关阅读:
    HTML学习 day04
    HTML学习 day03
    HTML学习 day02
    原生Js监听普通dom尺寸变化
    JavaScript-获取地址栏参数
    Window 下 MySQL 环境的安装
    JavaScript 中的12种循环遍历方法
    前端PS常用切图技巧
    requirejs教程(一):基本用法
    seajs教程(一):基本用法
  • 原文地址:https://www.cnblogs.com/tonglin0325/p/5961270.html
Copyright © 2011-2022 走看看