leetcode周赛128期真香
这一道题,其实还是蛮简单的。我直接用暴力的方式写的,先得到N的二进制原码表示,转化为反码之后,再使用我们简单的计算二进制真值的方法来计算即可。
class Solution {
public int bitwiseComplement(int N) {
String result=getBit(N);
return getInt(result);
}
public static String getBit(int N){//根据给定数字,获取其反码。
if(N==0) return "1";
String res="";
String temp="";
while(N!=0){
if(N%2==0){
res+="0";
}else{
res+="1";
}
N=N>>1;
}
res=new StringBuilder(res).reverse().toString();
for(int i=0;i<res.length();i++){
if(res.charAt(i)=='0') {
temp+="1";
}else{
temp+="0";
}
}
return new String(temp);
}
public static int getInt(String str) {//根据反码二进制的形式,得到对应的整形数字
int len=str.length();
int result=0;
for(int i=len-1;i>=0;i--) {
if(str.charAt(i)=='0'){
result+=0;
}else{
result+=Math.pow(2,len-i-1);
}
}
return result;
}
}
这道题,两层for循环的超时的,所以考虑O(N)的时间复杂度。类似于target=60的Two Sum问题。这里我没有采用HashMap,仅利用了一个数组,考虑到不同的值在对60取余之后,会得到相同的值,所以,利用桶的思想,存储相应的结果,对应的最后结果总和就是符合情况的。
class Solution {
public int numPairsDivisibleBy60(int[] time) {
int ans=0;
int [] count=new int[60];
for (int i=0; i<time.length;i++) {
ans+=count[(60-time[i]%60)%60];
count[time[i]%60]+=1;
}
return ans;
}
}
无脑跟discuss的,确实学到了解决问题的方法。首先,最大值的最小情况一定是大于数组中的max的,其次,最极端的情况就是D=1、所以,使用二分的思想,在max和sum之间使用二分查找,依次尝试对应的结果,类似的题目有leetcode 875、774
import java.util.*;
class Solution {
public int shipWithinDays(int[] weights, int D) {
//学习题目,使用二分法寻找临界值。
int sum=0;
int max=0;
for(int i=0;i<weights.length;i++) {
sum+=weights[i];
max=Math.max(max,weights[i]);
}
int left=max;
int right=sum;
while(left<right) {
int mid=left+(right-left)/2;
int cur=0;int need=1;
for(int w:weights) {
if(cur+w>mid) {
need+=1;
cur=0;
}
cur+=w;
}
if(need>D) {
left=mid+1;
}else right=mid;
}
return left;
}
}