今天刷了4道 LeetCode题,分别是:
- 1-bit and 2-bit Characters :
We have two special characters. The first character can be represented by one bit
0
. The second character can be represented by two bits (10
or11
).Now given a string represented by several bits. Return whether the last character must be a one-bit character or not. The given string will always end with a zero.
- Add Strings :bigInteger
- Array Partition I : Given an array of 2n integers, your task is to group these integers into n pairs of integer, say (a1, b1), (a2, b2), ..., (an, bn) which makes sum of min(ai, bi) for all i from 1 to n as large as possible.
- Backspace String Compare :Given two strings
S
andT
, return if they are equal when both are typed into empty text editors.#
means a backspace character.
对于第一题 1-bit and 2-bit Characters,难点在于需要仔细的分析问题的关键(思考过程需要从最后向前算,而且着重点在于找规律,如果找不出规律可以先举例子再归纳; 思考过程也可以从头向后看,需要分析的是,只要有1一定是2bit;)。
Solution1:从尾到头开始分析。需要注意的是不会存在01的组合,因此和末尾的0相邻的1出现的奇偶次数格外重要。
class Solution {
public boolean isOneBitCharacter(int[] bits) {
int length=bits.length;
int count=0;
if(bits[length-1]!=0){
return false;
}else{
for(int i=length-2;i>=0 && bits[i]==1;i--){
count++;
}
}
if(count % 2 == 0){
return true;
}else{
return false;
}
}
}
Solution2:从头到尾分析,可以发现从头起第一个0肯定是1bit,因为不会有01组合,那么接下来出现的1肯定是2bit。那么有一个方法就是设置一个指针来从头开始,遇到0就向前走1步,遇到1就向前走2步。如果最后一个0是1bit,那么指针会恰好停在0的index,如果最后一个0是2bit,那么指针会大于最后一个0的index,即index+1;
class Solution {
//这种方法很巧妙,需要在编程中学习并思考这种方法,pointer
public boolean isOneBitCharacter(int[] bits) {
int pointer=0;
while(pointer<bits.length-1){
pointer+=bits[pointer]+1;
}
return pointer==(bits.length-1);
}
}
对于第二题,Add Strings,大数加法;
Tip:如果直接输出str.charAt(),可以正常输出char字符,而不是ASCII码;如果和字符串相接,也是可以正常输出char字符,而不是ASCII;只有一种情况,但是如果把str.charAt()即char类型当成int进行计算,那么它将自动使用对应的ASCII来进行计算;比如'0'的ASCII为48;
Solution1:常规思维,先把两个数组倒序,长度短的后面补0。然后按index把每一位相加,结果保留,有进位的话在下一位相加时多加1,最后把这些字符串连起来就是结果。
Solution2: 思维方法和上面相似,代码上可以更加精简。不需要倒序,直接使用for循环倒着遍历,并且合并两个for循环到一个for循环上。最后有一点注意的是,每一位相加的结果 result%10 就是需要保存的,result / 10就是代表是否需要进位的。
class Solution {
public String addStrings(String num1, String num2) {
int overFlow=0;
StringBuffer res= new StringBuffer();
for(int i=num1.length()-1,j=num2.length()-1;i>=0 || j>=0 || overFlow==1; i--,j--){
int wei1= i<0 ? 0: num1.charAt(i)-'0';
int wei2= j<0 ? 0: num2.charAt(j)-'0';
int append= (wei1 + wei2 + overFlow) % 10;
res.append(append);
overFlow= (wei1 + wei2 + overFlow) / 10;
}
return res.reverse().toString();
}
}
对于第三题,Array Partition I,实际上就是排序算法,先把数组排序后,取奇数index所对应的值的和就是最终结果。
我使用了快排。
class Solution {
public int arrayPairSum(int[] nums) {
quickSort(nums);
int sum=0;
for(int i=0;i<nums.length;i+=2){
sum+=nums[i];
}
return sum;
}
public static void quickSort(int[] arr){
qsort(arr, 0, arr.length-1);
}
private static void qsort(int[] arr, int low, int high){
if (low < high){
int pivot=partition(arr, low, high); //将数组分为两部分
qsort(arr, low, pivot-1); //递归排序左子数组
qsort(arr, pivot+1, high); //递归排序右子数组
}
}
private static int partition(int[] arr, int low, int high){
int pivot = arr[low]; //枢轴记录
while (low<high){
while (low<high && arr[high]>=pivot) --high;
arr[low]=arr[high]; //交换比枢轴小的记录到左端
while (low<high && arr[low]<=pivot) ++low;
arr[high] = arr[low]; //交换比枢轴小的记录到右端
}
//扫描完成,枢轴到位
arr[low] = pivot;
//返回的是枢轴的位置
return low;
}
}
对于第四题,Backspace String Compare , 自己的想法是可以用栈的结构来做,但是结果运行速度不够理想。然后使用了暴力法,发现速度比栈的做法快。
List<Character> 是char类型的List,List中的类型都必须是包装类,不能为原始类型如char,int;
如果用原始类型会报错:Syntax error, insert "Dimensions" to complete ReferenceType;
class Solution {
public boolean backspaceCompare(String S, String T) {
StringBuffer str1= new StringBuffer();
StringBuffer str2= new StringBuffer();
List<Character> results1=new ArrayList<Character>();
List<Character> results2=new ArrayList<Character>();
for(int i=0;i<S.length();i++){
if(S.charAt(i) == '#'){
pop(results1);
}else{
push(S.charAt(i),results1);
}
}
for(int i=0;i<T.length();i++){
if(T.charAt(i) == '#'){
pop(results2);
}else{
push(T.charAt(i),results2);
}
}
for(char c:results1){
str1.append(c);
}
for(char c:results2){
str2.append(c);
}
return str1.toString().equals(str2.toString());
}
public void push(char c,List results){
results.add(c);
}
public void pop(List results){
if(results.size()==0)
return;
results.remove(results.size()-1);
}
}
方法2
class Solution {
public boolean backspaceCompare(String S, String T) {
int maxLength= S.length()>T.length() ? S.length() : T.length();
StringBuffer str1=new StringBuffer();
StringBuffer str2=new StringBuffer();
for(int i=0;i<maxLength;i++){
if(i<S.length()){
if(S.charAt(i)=='#'){
if(str1.length()!=0){
str1.deleteCharAt(str1.length()-1);
}
}else{
str1.append(S.charAt(i));
}
}
if(i<T.length()){
if(T.charAt(i)=='#'){
if(str2.length()!=0){
str2.deleteCharAt(str2.length()-1);
}
}else{
str2.append(T.charAt(i));
}
}
}
return str1.toString().equals(str2.toString());
}
}