한 배열에 다른 배열의 모든 요소가 포함되어 있는지 확인하는 방법
주어진:
a1 = [5, 1, 6, 14, 2, 8]
다음의 모든 요소가 포함되어 있는지 확인하고 싶습니다.
a2 = [2, 6, 15]
이 경우 결과는 다음과 같습니다.false
.
이러한 어레이 포함을 식별할 수 있는 내장 Ruby/Rails 방법이 있습니까?
이를 구현하는 한 가지 방법은 다음과 같습니다.
a2.index{ |x| !a1.include?(x) }.nil?
더 좋고, 더 읽기 쉬운 방법이 있을까요?
a = [5, 1, 6, 14, 2, 8]
b = [2, 6, 15]
a - b
# => [5, 1, 14, 8]
b - a
# => [15]
(b - a).empty?
# => false
아마도 이것은 읽기가 더 쉬울 것입니다.
a2.all? { |e| a1.include?(e) }
배열 교차를 사용할 수도 있습니다.
(a1 & a2).size == a1.size
참고:size
여기서는 속도를 위해 사용되며, 다음 작업도 수행할 수 있습니다(예:
(a1 & a2) == a1
하지만 저는 첫 번째가 더 읽기 쉽다고 생각합니다.이 3개는 일반 루비(레일이 아님)입니다.
이는 다음을 수행하여 달성할 수 있습니다.
(a2 & a1) == a2
이렇게 하면 두 배열의 교차점이 생성되어 모든 요소가 반환됩니다.a2
에도 있는 것들a1
결과가 다음과 같을 경우a2
모든 요소가 에 포함되어 있는지 확인할 수 있습니다.a1
.
이 접근 방식은 다음의 모든 요소에 해당하는 경우에만 작동합니다.a2
애당초 서로 다릅니다.중복이 있는 경우 이 접근 방식은 실패합니다.Tempos에서 온 것은 여전히 작동하므로, 저는 진심으로 그의 접근법을 추천합니다(또한 아마도 더 빠를 것입니다).
중복 요소가 없거나 요소에 관심이 없는 경우 Set 클래스를 사용할 수 있습니다.
a1 = Set.new [5, 1, 6, 14, 2, 8]
a2 = Set.new [2, 6, 15]
a1.subset?(a2)
=> false
이것이 사용하는 배경에는
all? { |o| set.include?(o) }
배열 클래스에 원숭이 패치를 적용할 수 있습니다.
class Array
def contains_all?(ary)
ary.uniq.all? { |x| count(x) >= ary.count(x) }
end
end
시험
irb(main):131:0> %w[a b c c].contains_all? %w[a b c]
=> true
irb(main):132:0> %w[a b c c].contains_all? %w[a b c c]
=> true
irb(main):133:0> %w[a b c c].contains_all? %w[a b c c c]
=> false
irb(main):134:0> %w[a b c c].contains_all? %w[a]
=> true
irb(main):135:0> %w[a b c c].contains_all? %w[x]
=> false
irb(main):136:0> %w[a b c c].contains_all? %w[]
=> true
irb(main):137:0> %w[a b c d].contains_all? %w[d c h]
=> false
irb(main):138:0> %w[a b c d].contains_all? %w[d b c]
=> true
물론 이 방법은 표준 단독 방법으로 작성할 수 있습니다.
def contains_all?(a,b)
b.uniq.all? { |x| a.count(x) >= b.count(x) }
end
그리고 당신은 그것을 다음과 같이 호출할 수 있습니다.
contains_all?(%w[a b c c], %w[c c c])
실제로 프로파일링 후 다음 버전이 훨씬 빠르고 코드가 더 짧습니다.
def contains_all?(a,b)
b.all? { |x| a.count(x) >= b.count(x) }
end
(a1 - a2) 또는 (a1 및 a2)를 기반으로 한 대부분의 답변은 두 배열에 중복 요소가 있는 경우 작동하지 않습니다.저는 단어의 모든 문자(열로 분할)가 (스크래블 등의) 문자 집합의 일부인지 확인하는 방법을 찾아 여기에 도착했습니다.이 답변들 중 어느 것도 효과가 없었지만, 이 답변은 다음과 같습니다.
def contains_all?(a1, a2)
try = a1.chars.all? do |letter|
a1.count(letter) <= a2.count(letter)
end
return try
end
어레이 크기에 따라 효율적인 알고리즘 O(n log n)를 고려할 수 있습니다.
def equal_a(a1, a2)
a1sorted = a1.sort
a2sorted = a2.sort
return false if a1.length != a2.length
0.upto(a1.length - 1) do
|i| return false if a1sorted[i] != a2sorted[i]
end
end
정렬 비용 O(n log n) 및 각 쌍 확인 비용 O(n)이므로 이 알고리즘은 O(n log n)입니다.다른 알고리즘은 정렬되지 않은 어레이를 사용하여 (점근적으로) 더 빠를 수 없습니다.
하나의 배열을 찾으려 할 때 이 게시물로 향했습니다.["a", "b", "c"]
다른 배열을 포함했습니다.["a", "b"]
나의 경우 동일한 주문이 질문에 대한 추가적인 요구 사항이었습니다.
다음은 이러한 추가 요구사항이 있는 모든 사용자를 위한 솔루션(O(n) 복잡성이라고 생각됨)입니다.
def array_includes_array(array_to_inspect, array_to_search_for)
inspectLength = array_to_inspect.length
searchLength = array_to_search_for.length
if searchLength == 0 then
return true
end
if searchLength > inspectLength then
return false
end
buffer = []
for i in 0..inspectLength
buffer.push(array_to_inspect[i])
bufferLastIndex = buffer.length - 1
if(buffer[bufferLastIndex] != array_to_search_for[bufferLastIndex]) then
buffer.clear
next
end
if(buffer.length == searchLength) then
return true
end
end
return false
end
이렇게 하면 테스트 결과가 생성됩니다.
puts "1: #{array_includes_array(["a", "b", "c"], ["b", "c"])}" # true
puts "2: #{array_includes_array(["a", "b", "c"], ["a", "b"])}" # true
puts "3: #{array_includes_array(["a", "b", "c"], ["b", "b"])}" # false
puts "4: #{array_includes_array(["a", "b", "c"], ["c", "b", "a"])}" # false
puts "5: #{array_includes_array(["a", "b", "c"], [])}" # true
puts "6: #{array_includes_array([], ["a"])}" # false
puts "7: #{array_includes_array([], [])}" # true
언급URL : https://stackoverflow.com/questions/7387937/how-to-determine-if-one-array-contains-all-elements-of-another-array
'source' 카테고리의 다른 글
Excel VBA를 사용하여 SQL 조회 실행 (0) | 2023.05.26 |
---|---|
항목을 수평으로 배치하는 WPF ListBox (0) | 2023.05.26 |
반 플로트 숫자를 적절하게 반올림하는 방법은 무엇입니까? (0) | 2023.05.26 |
div에서 텍스트를 수직으로 정렬하려면 어떻게 해야 합니까? (0) | 2023.05.26 |
각도 2를 사용한 HTML5 이벤트 처리(포커스 및 포커스 아웃) (0) | 2023.05.26 |