問題の説明
並べ替え
られた配列の要素の最初と最後の位置を検索します。昇順の整数配列numsとターゲット値targetが与えられます。配列内の指定されたターゲット値の開始位置と終了位置を見つけます。
アルゴリズムの時間の複雑さはO(log n)レベルでなければなりません。
配列にターゲット値がない場合は、[-1、-1]を返します。
例1:
入力:nums = [5,7,7,8,8,10]、ターゲット= 8
出力:[3,4]
例2:
入力:nums = [5,7,7,8,8,10 ]、ターゲット= 6
出力:[-1、-1]
解決
まず、この方法は、スペースの複雑さに関係なく考えるのに適した方法であり、配列を走査してターゲットを見つけた後、それを後で表示するのではなく、最初に表示されるかどうかを判断します。しかし、問題は空間の複雑さをO(log n)にする必要があります。この方法はサイクルが多すぎるため、明らかに間違っています。
次に、タイトルが昇順の配列であることを示していることに気づくことができます。昇順の配列を思いのままに考えるのは難しくありません。
コード
int[] nums = {
5,7,7,8,8,10};
int[] a = {
-1,-1};
int target = 8;
//方法1
for (int i=0;i<nums.length;i++){
if(nums[i]==target){
if (a[0]==-1){
a[0] = i;
}else{
a[1] = i;
}
}
}
for (Integer i:a) {
System.out.println(i);
}
//方法2
int left = 0;
int right = nums.length-1;
while(left<=right){
int mid = (left + right)/2;
if(nums[mid]==target){
while(mid>=left && nums[mid]==target){
mid--;
}
a[0] = mid+1;
mid = (left + right)/2;
while(mid<=right && nums[mid]==target){
mid++;
}
a[1] = mid - 1;
break;
}else if (nums[mid] > target){
right = mid-1;
}else{
left = mid+1;
}
}
for (Integer i:a) {
System.out.println(i);
}
総括する
方法1と方法2を比較すると、二分法を使用したコードが本当に長いことを見つけるのは難しくありませんが、方法2はトピックのスペースの複雑さの要件を満たしています。