2017-11-30 13 views
2

기존 배열의 배열 값 범위를 반환하는 더 나은 방법을 찾고 있습니다. 번호의리스트/어레이 주어진 항목을 중심으로 배열의 하위 집합을 찾습니다.

는 말 :

[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

난의 범위를 선택하려는 주어진 숫자 x를 중심으로 한 5 개의 숫자. x가 4 인 경우

(Psuedocode 내가 정말 여기에 배열 인덱스를 참조 것 같아 이후 .. 값이 할 문제가 단지 위치)

그래서, 우리는 그 중심 범위를 반환 할 수 있습니다

[2, 3, 4, 5, 6]

그러나 x가 2 인 경우, 우리는 범위를 중심으로 수 없습니다, 그래서 우리는 우리의 최선을 반환해야 할 것 :

[1, 2, 3, 4, 5]

... 중심에 있지 않지만 적어도 5 개의 숫자를 반환했습니다.

는 X는 10 마찬가지로 경우 :

[5, 6, 7, 8, 9, 10]

... (10)는 한계 때문에 불가능 중심 때문에 5 개 개의 번호가 뒤로 밀려 .

일부 JS 코드에서이 작업을 수행 할 수 있지만 조건이 너무 많은 코드가 너무 많습니다.

알려진 방법이나 알고리즘이 도움이 될지 궁금하십니까?

+0

, 당신은 항상 중앙 인덱스를 선택, 당신은 쉽게 센터와 다른 부분 집합의 왼쪽에서 하위 집합을 선택에 문제가 깨질 수 센터의 오른쪽에서 항상 솔루션이 있다고 가정하면 측면에서 더 많은 요소를 전달해야 할 때 쉽게 계산할 수 있습니다. 부분 집합을 선택하는 것은 충분히 간단해야합니다. – AlexITC

+0

이 코드는 [codereview] (https://codereview.stackexchange.com/)에 가장 적합하다고 생각합니다. 여기에 잘 맞지 않아요. – Sebivor

+0

@Sebivor, 여기 코드가 없으므로 codereview가 없습니다. –

답변

4

다음과 같이 할 수 있습니다.

가변 개수와 일반 용액

var arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]; 
 

 

 
function findSubset(arr, item) { 
 
    // check index 
 
    var index = arr.indexOf(item); 
 
    // if element not found then return 
 
    if (index == -1) return; 
 

 
    // if element is at starting position 
 
    // then return first 5 element 
 
    if (index < 3) 
 
    return arr.slice(0, 5); 
 

 
    // if elements at ending position 
 
    // then return last 5 elements 
 
    if (index > arr.length - 4) 
 
    return arr.slice(-5); 
 

 
    // otherwisse return elements based on the index 
 
    // within the required range 
 
    return arr.slice(index - 2, index + 3); 
 
} 
 

 
console.log(
 
    findSubset(arr, 1), 
 
    findSubset(arr, 10), 
 
    findSubset(arr, 5), 
 
    findSubset(arr, 9), 
 
    findSubset(arr, 3) 
 
)
.

var arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]; 
 

 

 
function findSubset(arr, item, count = 5) { 
 
    var index = arr.indexOf(item), 
 
    // calculate floor and ceil value for comparison 
 
    // and getting subset array 
 
    f = Math.floor(count/2), 
 
    c = Math.ceil(count/2); 
 
    
 
    if (index == -1) return; 
 
    
 
    if (index < c) 
 
    return arr.slice(0, count); 
 

 
    if (index > arr.length - c - 1) 
 
    return arr.slice(-count); 
 

 
    return arr.slice(index - 2, index + c); 
 
} 
 

 
console.log(
 
    findSubset(arr, 1, 3), 
 
    findSubset(arr, 10, 7), 
 
    findSubset(arr, 5, 1), 
 
    findSubset(arr, 9, 4), 
 
    findSubset(arr, 8, 1), 
 
    findSubset(arr, 7, 3), 
 
    findSubset(arr, 3, 9) 
 
)
아래 알고리즘  의

0

레시피 :

  1. 는 최대 길이 a.length의 부분 집합 s을 만듭니다.
  2. 시작 인덱스를 계산합니다. 인덱스는 x이고, 길이의 절반에서 s을 뺀 값입니다.
  3. 색인 오버플로를 방지하기 위해 시작 색인을 조정하십시오.
  4. s.lengtha부터 s까지의 항목을 복사하십시오.
  5. 돌아 가기 s.

배열 ss 이후 배열 a에 포함되도록 보장하는 것은 a보다 결코 더 크다. 당신이 그것을 제공하지 않았기 때문에이 자신의 코드보다 짧은 있는지

var a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]; 
 

 
function subset (a, x, n) { 
 
    var s = new Array(Math.min(a.length, n)); 
 
    var j = a.indexOf(x) - Math.floor(s.length/2); 
 
    // overlap to the left : [.[1]2 3 4] 
 
    if (j < 0) { 
 
    j = 0; 
 
    } 
 
    // overlap to the right : [1 2 3[4].] 
 
    else if (j > a.length - s.length) { 
 
    j = a.length - s.length; 
 
    } 
 
    for (var i = 0; i < s.length; i++) { 
 
    s[i] = a[j + i] 
 
    } 
 
    return s; 
 
} 
 

 
console.log("x = 2, n = 4, s =", subset(a, 2, 4).join(",")); 
 
console.log("x = 9, n = 4, s =", subset(a, 9, 4).join(",")); 
 
console.log("x = 5, n = 4, s =", subset(a, 5, 4).join(",")); 
 
console.log("x = 2, n = 5, s =", subset(a, 2, 5).join(",")); 
 
console.log("x = 9, n = 5, s =", subset(a, 9, 5).join(",")); 
 
console.log("x = 5, n = 5, s =", subset(a, 5, 5).join(",")); 
 
console.log("x = 5, n = 20, s =", subset(a, 5, 20).join(","));

하지만, 하드는 알 - |

2

절반 크기를 뺀 값을 빼고 음수 인덱스는 최대 값을, 배열 길이에서 원하는 하위 배열 크기를 뺀 값보다 큰 인덱스 값을 취할 수 있습니다. 내가 알고있는 것처럼

value array       index adj max min 
----- ------------------------------ ----- --- --- --- 
      v        
    2 1, 2, 3, 4, 5, 6, 7, 8, 9, 10  1 -1 0 0 
     [    ] 

        v   
    5 1, 2, 3, 4, 5, 6, 7, 8, 9, 10  4  2 2 2 
       [    ] 

            vv   
    10 1, 2, 3, 4, 5, 6, 7, 8, 9, 10  9  7 7 5 
         [    ] 

function getSub(array, value, size) { 
 
    var index = array.indexOf(value) - (size - 1)/2, 
 
     max = Math.max(index, 0), 
 
     min = Math.min(max, array.length - size); 
 
    return array.slice(min, min + size); 
 
} 
 

 
console.log(getSub([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 2, 5)); 
 
console.log(getSub([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 5, 5)); 
 
console.log(getSub([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 10, 5));
.as-console-wrapper { max-height: 100% !important; top: 0; }

+0

'.slice'가 잘라내지만'size >> 1' 또는'size/2'는 괜찮을 것입니다. – Slai

+0

@Slai, 나는 크기의 값이 항상 있다고 생각합니다. 중간 인덱스가있는 구조 때문에 이상합니다. –

+0

죄송합니다, 절대 신경 쓰지 마세요. - 1이 더 적당 할 것 같습니다. – Slai