LintCode算法题目 容易(二)

第一题 Strings Homomorphism

Given two strings s and t, determine if they are isomorphic.

Two strings are isomorphic if the characters in s can be replaced to get t.

All occurrences of a character must be replaced with another character while preserving the order of characters. No two characters may map to the same character but a character may map to itself.

 注意事项

You may assume both s and t have the same length.

样例

Given s = "egg", t = "add", return true.

Given s = "foo", t = "bar", return false.

Given s = "paper", t = "title", return true.

注: 将字母作为键,判断是否重复。

  public boolean isIsomorphic(String s, String t) {
        
        int[] flag1 = new int[s.length()];
    	int[] flag2 = new int[t.length()];
    	if(flag1.length != flag2.length){
    		return false;
    	}
    	HashMap<Character, Integer> map1 = new HashMap<>();
    	HashMap<Character, Integer> map2 = new HashMap<>();
    	int tmp = 0;
    	for(int i = 0 ; i < s.length(); i ++){
    		if(!map1.containsKey(s.charAt(i))){
    			map1.put(s.charAt(i), tmp);
    			tmp++;
    			flag1[i] = tmp;
    			
	    	}else{  
	            flag1[i] = map1.get(s.charAt(i));  
	        } 
    	}
    	tmp = 0 ;
    	for(int i = 0 ; i < t.length(); i ++){
    		if(!map2.containsKey(t.charAt(i))){
    			map2.put(t.charAt(i), tmp);
    			tmp++;
    			flag2[i] = tmp;
	    	}else{  
	            flag2[i] = map2.get(t.charAt(i));  
	        } 
    		if(flag1[i] != flag2[i]){
    			return false;
    		}
    	}
    	return true;
    }

第二题 First Position Unique Character

 

Given a string, find the first non-repeating character in it and return it's index. If it doesn't exist, return -1.

样例

Given s = "lintcode", return 0.

Given s = "lovelintcode", return 2.

   public int firstUniqChar(String s) {
        	 if(s == null || s.length() == 0){  
             return -1;  
         }  
         for(int i = 0; i<s.length() - 1; i++){  
             char p = s.charAt(i);  
             if(s.indexOf(p , i + 1) < 0 && s.indexOf(p) == i){  
                 return i;  
             }  
         }  
         if(s.indexOf(s.charAt(s.length() - 1)) == s.length() - 1){  
             return s.length() - 1;  
         }  
         return -1;  
    }

第三题 各位相加

给出一个非负整数 num,反复的将所有位上的数字相加,直到得到一个一位的整数。

样例

给出 num = 38。

相加的过程如下:3 + 8 = 11,1 + 1 = 2。因为 2 只剩下一个数字,所以返回2。

   public int addDigits(int num) {
        if(num < 10){
    		return num;
    	}
        int[] number = new int[20];
        int i = 0;
        int sum = 0;
    	while(num > 0){
    		number[i] = num % 10;
    		i++;
    		num = num / 10;
        }
    	for(int j = 0 ; j < i ; j ++){
    		sum += number[j];
    	}
    	if(sum >= 10){
    		return addDigits(sum);
    	}else{
    		return sum;
    	}
    }

挑战 

你可以不用任何的循环或者递归算法,在 O(1) 的时间内解决这个问题么?

  public static int addDigits(int num) {
        String numStr = Integer.toString(num);
        while(numStr.length() > 1) {
            int sum = 0;
            for(int i = 0; i < numStr.length(); i++) {
                sum = sum + Character.getNumericValue(numStr.charAt(i));
                System.out.println(Character.getNumericValue(numStr.charAt(i)));
            }
            numStr = Integer.toString(sum);
        }

        return Integer.parseInt(numStr);
    }

第四题 移动零

题目

给一个数组 nums 写一个函数将0

移动到数组的最后面,非零元素保持原数组的顺序

注意事项

1.必须在原数组上操作

2.最小化操作数

样例给出 nums =[0, 1, 0, 3, 12], 调用函数之后, nums =[1, 3, 12, 0, 0]

分析

这类数组原地删除数据的题目,考察的就是两根指针的应用,注意掌握两根指针的思想,这一类问题就可以迎刃而解了。

我们设置两根指针slow和fast,fast每次都递增,所以称之为fast,当遍历到不是0的时候,slow指针就存储fast此时遍历的元素,slow加一,当遍历到需要删除的元素0(就相当于移动0到最后)时,略过slow,直接fast++,相当于删除了0.同时设置一个变量记录新数组的长度。

最后我们再遍历剩下的元素,并给他们赋值为0即可。

这道题可以看作是删除元素那道题的扩展应用

#代码

 public void moveZeroes(int[] nums) {
        int show = 0;
        for(int i = 0 ; i < nums.length; i ++){
        	if(nums[i] != 0 ){
        		nums[show] = nums[i];
        		show++;
        	}
        }
        for(int i = show; i < nums.length; i ++){
        	nums[i] = 0;
        }
    }

 

第五题 玩具工厂 

工厂模式是一种常见的设计模式。请实现一个玩具工厂 ToyFactory 用来产生不同的玩具类。可以假设只有猫和狗两种玩具。

 

样例

ToyFactory tf = ToyFactory(); Toy toy = tf.getToy('Dog'); toy.talk(); >> Wow toy = tf.getToy('Cat'); toy.talk(); >> Meow


interface Toy {
    void talk();
}

class Dog implements Toy {
   public void talk(){
	   System.out.println("Wow");
   }
}

class Cat implements Toy {
   public void talk(){
	   System.out.println("Meow");
   }
}

public class ToyFactory {
    Dog dog = new Dog();
    Cat cat = new Cat();
    public Toy getToy(String type) {
    	if(type.equals("Dog")){
    		return dog;
    	}
    	if(type.equals("Cat")){
    		return cat;
    	}
    	return null;
    }
}

第六题 左填充

实现一个leftpad库,如果不知道什么是leftpad可以看样例

样例

leftpad("foo", 5) >> " foo" leftpad("foobar", 6) >> "foobar" leftpad("1", 2, "0") >> "01"

public class StringUtils {
    
   static public String leftPad(String originalStr, int size) {
        if (originalStr.length() >= size){
            return originalStr;
        }
        StringBuffer sbr = new StringBuffer();
        if(originalStr.length() < size){
            for(int i = originalStr.length(); i < size; i ++){
                sbr.append(" ");
            }
            sbr.append(originalStr);
        }
        return sbr.toString();
    }

   
    static public String leftPad(String originalStr, int size, char padChar) {
    	StringBuffer sbNew = new StringBuffer();
    	if (originalStr.length() >= size){
            return originalStr;
        }
    	if(originalStr.length() < size){
    		for(int i = originalStr.length(); i < size; i ++){
    			sbNew.append(padChar);
            }
    		sbNew.append(originalStr);   		
    	}
    	return sbNew.toString();
    }
}

第七题 丑数

写一个程序来检测一个整数是不是丑数。

丑数的定义是,只包含质因子 2, 3, 5 的正整数。比如 6, 8 就是丑数,但是 14 不是丑数以为他包含了质因子 7。

 注意事项

可以认为 1 是一个特殊的丑数。

 

样例

给出 num = 8,返回 true。

给出 num = 14,返回 false。

public boolean isUgly(int num) {
        if(num == 1){
    		return true;
    	}
    	if(num <= 0){
    	    return false;
    	}
    	while(num >= 2 ){
    		if(num % 2 == 0){
    			num = num / 2;
    			continue;
    		}else if(num % 3 == 0){
    			num = num / 3;
    			continue;
    		}else if(num % 5 == 0){
    			num = num / 5;
    			continue;
    		}else{
    			return false;
    		}
    	}
    	return true;    
        
    }

第八题 栅栏染色

我们有一个栅栏,它有n个柱子,现在要给柱子染色,有k种颜色可以染。

必须保证任意两个相邻的柱子颜色不同,求有多少种染色方案。

 注意事项

n和k都是非负整数

 

样例

n = 3, k = 2, return 6

post 1, post 2, post 3 way1 0 0 1 way2 0 1 0 way3 0 1 1 way4 1 0 0 way5 1 0 1 way6 1 1 0

 

问题描述

 

lintcode表述有问题,原文是“必须保证任意两个相邻的柱子颜色不同,应该表述为“不能有连续三个柱子颜色相同”。

参考

LintCode:栅栏染色 

参考里改掉的表述感觉也不对,还是应该说“不能有连续三个柱子颜色相同”。

笔记

在改掉问题表述的情况下: 

假设buff[i]为有i个柱子时的染色方案。可以分为两种情况: 

1. 最后两个柱子颜色相同。 

前i-2个柱子已经有buff[i-2]种方案了,第i-1个和第i个柱子取相同的颜色,但是要和i-2个柱子不同,有(k-1)种取法。 

2. 最后两个柱子颜色不同。 

前i-1个柱子符合要求,已经有buff[i-1]种方案了,第i个柱子的颜色要和第i-1个柱子颜色不同,还有(k-1)种方案。 

由此,状态转移方程为:

buff[i] = buff[i-1] * (k-1) + buff[i-2] * (k-1);

初始条件: 

buff[1] = k; buff[2] = k*k;

 

  public int numWays(int n, int k) {
      	if (n == 0) {
			return 0;
		}
		if (n == 1) {
			return k;
		}
		if (n == 2) {
			return k * k;
		}
		int pre = k;
		int now = k * k;
		for (int i = 3; i <= n; i++) {
			int tmp = now;
			now = (pre + now) * (k - 1);
			pre = tmp;
		}
		return now;
    }

 

第九题 单词计数

使用 map reduce 来计算单词频率

https://hadoop.apache.org/docs/r1.2.1/mapred_tutorial.html#Example%3A+WordCount+v1.0

 

样例

chunk1: "Google Bye GoodBye Hadoop code" chunk2: "lintcode code Bye" Get MapReduce result: Bye: 2 GoodBye: 1 Google: 1 Hadoop: 1 code: 2 lintcode: 1

 

/**
 * Definition of OutputCollector:
 * class OutputCollector<K, V> {
 *     public void collect(K key, V value);
 *         // Adds a key/value pair to the output buffer
 * }
 */
public class WordCount {

    public static class Map {
        public void map(String key, String value, OutputCollector<String, Integer> output) {
            String[] tmp = value.split(" ");  
            for(int i = 0;i < tmp.length;i++){  
                output.collect(tmp[i],1);  
            }  
        }
    }

    public static class Reduce {
        public void reduce(String key, Iterator<Integer> values,
                           OutputCollector<String, Integer> output) {
            int count = 0;    
            while(values.hasNext()){    
                count += values.next();    
            }    
            output.collect(key , count); 
        }
    }
}

第十题 快乐数

写一个算法来判断一个数是不是"快乐数"。

一个数是不是快乐是这么定义的:对于一个正整数,每一次将该数替换为他每个位置上的数字的平方和,然后重复这个过程直到这个数变为1,或是无限循环但始终变不到1。如果可以变为1,那么这个数就是快乐数。

 

样例

19 就是一个快乐数。

1^2 + 9^2 = 82 8^2 + 2^2 = 68 6^2 + 8^2 = 100 1^2 + 0^2 + 0^2 = 1

   private static int COUNT = 0;
    public  boolean isHappy(int n) {
    	if(n < 0 ){
    		return false;
    	}
    	if(n == 1){
    		return true;
    	}
		int[] number = new int[10];
		int i = 0;
    	while ( n > 0){
    		number[i] = n % 10;
    		n = n / 10;
    		i++;
    	}
    	int sum = 0 ;
    	for(i = 0 ; i < number.length; i++){
    		sum += (number[i] * number[i]);
    	}
    	if(sum == 1){
    		return true;
    	}else{
    		COUNT = COUNT + 1;
    		if(COUNT > 20){
    			return false;
    		}else{
    			return isHappy(sum);
    		}
    	}
    }

 

转载于:https://my.oschina.net/hxflar1314520/blog/917313

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值