给定一个数组nrr [] ,该数组由[L,R]形式的N个间隔组成,其中L,R表示该间隔的开始和结束位置,任务是计算一个间隔可以与之相交的最大间隔数彼此。
例子:
Input: arr[] = {{1, 2}, {3, 4}, {2, 5}}
Output: 3
Explanation: The required set of intervals are {1, 2}, {2, 5}, {3, 4} as {2, 5} intersect all other intervals.
Input: arr[] = {{1, 3}, {2, 4}, {3, 5}, {8, 11}}
Output: 3
Explanation: The required set of intervals are {1, 3}, {2, 4}, {3, 5} as {2, 4} intersect all other intervals.
天真的方法:最简单的方法是遍历数组,并为每个间隔使用嵌套循环计算相交的间隔数。检查每个间隔后,打印一个间隔可以相交的最大间隔数。
下面是上述方法的实现:
C++
// C++ program for the above approach
#include
using namespace std;
// Function to count the maximum number
// of intervals that an interval
// can intersect
void findMaxIntervals(
vector > v, int n)
{
// Store the required answer
int maxi = 0;
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Store the number of
// intersecting intervals
int c = n;
// Iterate in the range[0, n-1]
for (int j = 0; j < n; j++) {
// Check if jth interval lies
// outside the ith interval
if (v[i].second < v[j].first
|| v[i].first > v[j].second) {
c--;
}
}
// Update the overall maximum
maxi = max(c, maxi);
}
// Print the answer
cout << maxi;
}
// Driver Code
int main()
{
vector > arr
= { { 1, 2 },
{ 3, 4 },
{ 2, 5 } };
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
return 0;
}
Java
// Java implementation of the approach
import java.util.*;
class GFG
{
static class Pair
{
int first, second;
public Pair(int first, int second)
{
this.first = first;
this.second = second;
}
}
// Function to count the maximum number
// of intervals that an interval
// can intersect
static void findMaxIntervals(ArrayList v, int n)
{
// Store the required answer
int maxi = 0;
// Traverse all the intervals
for (int i = 0; i < n; i++)
{
// Store the number of
// intersecting intervals
int c = n;
// Iterate in the range[0, n-1]
for (int j = 0; j < n; j++) {
// Check if jth interval lies
// outside the ith interval
if (v.get(i).second < v.get(j).first
|| v.get(i).first > v.get(j).second) {
c--;
}
}
// Update the overall maximum
maxi = Math.max(c, maxi);
}
// Print the answer
System.out.print(maxi);
}
// Driver code
public static void main(String[] args)
{
ArrayList arr = new ArrayList<>();
arr.add(new Pair(1,2));
arr.add(new Pair(3,4));
arr.add(new Pair(2,5));
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
}
}
// This code is contributed by susmitakundugoaldnga.
Python3
# Python3 program for the above approach
# Function to count the maximum number
# of intervals that an interval
# can intersect
def findMaxIntervals(v, n) :
# Store the required answer
maxi = 0
# Traverse all the intervals
for i in range(n) :
# Store the number of
# intersecting intervals
c = n
# Iterate in the range[0, n-1]
for j in range(n) :
# Check if jth interval lies
# outside the ith interval
if (v[i][1] < v[j][0] or v[i][0] > v[j][1]) :
c -= 1
# Update the overall maximum
maxi = max(c, maxi)
# Print the answer
print(maxi)
# Driver code
arr = []
arr.append((1,2))
arr.append((3,4))
arr.append((2,5))
N = len(arr)
# Function Call
findMaxIntervals(arr, N)
# This code is contributed by divyeshrabadiya07.
C#
// C# program for the above approach
using System;
using System.Collections.Generic;
class GFG
{
// Function to count the maximum number
// of intervals that an interval
// can intersect
static void findMaxIntervals(List > v, int n)
{
// Store the required answer
int maxi = 0;
// Traverse all the intervals
for (int i = 0; i < n; i++)
{
// Store the number of
// intersecting intervals
int c = n;
// Iterate in the range[0, n-1]
for (int j = 0; j < n; j++)
{
// Check if jth interval lies
// outside the ith interval
if (v[i].Item2 < v[j].Item1
|| v[i].Item1 > v[j].Item2)
{
c--;
}
}
// Update the overall maximum
maxi = Math.Max(c, maxi);
}
// Print the answer
Console.Write(maxi);
}
// Driver code
static void Main()
{
List> arr = new List>();
arr.Add(new Tuple(1,2));
arr.Add(new Tuple(3,4));
arr.Add(new Tuple(2,5));
int N = arr.Count;
// Function Call
findMaxIntervals(arr, N);
}
}
// This code is contributed by divyesh072019.
C++
// C++ program for the above approach
#include
using namespace std;
// Comparator function to sort in
// increasing order of second
// values in each pair
bool compare(pair f,
pair s)
{
return f.second < s.second;
}
// Function to hash a pair
struct hash_pair {
template
size_t operator()(
const pair& p) const
{
auto hash1 = hash{}(p.first);
auto hash2 = hash{}(p.second);
return hash1 ^ hash2;
}
};
// Function to count maximum number
// of intervals that an interval
// can intersect
void findMaxIntervals(
vector > v, int n)
{
// Create a hashmap
unordered_map,
int,
hash_pair>
um;
// Sort by starting position
sort(v.begin(), v.end());
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Initalize um[v[i]] as 0
um[v[i]] = 0;
// Store the starting and
// ending point of the
// ith interval
int start = v[i].first;
int end = v[i].second;
// Set low and high
int low = i + 1;
int high = n - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to find
// the number of intervals
// completely lying to the
// right of the ith interval
while (low <= high) {
// Find the mid
int mid = low + (high - low) / 2;
// Condition for searching
// in the first half
if (v[mid].first > end) {
ans = mid;
high = mid - 1;
}
// Otherwise search in the
// second half
else {
low = mid + 1;
}
}
// Increment um[v[i]] by n-ans
// if ans!=-1
if (ans != -1)
um[v[i]] = n - ans;
}
// Sort by ending position
sort(v.begin(), v.end(), compare);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Store the starting and
// ending point of the
// ith interval
int start = v[i].first;
int end = v[i].second;
// Set low and high
int low = 0;
int high = i - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to
// find the number of intervals
// completely lying to the
// left of the ith interval
while (low <= high) {
int mid = low + (high - low) / 2;
if (v[mid].second < start) {
ans = mid;
low = mid + 1;
}
else {
high = mid - 1;
}
}
// Increment um[v[i]] by ans+1
// if ans!=-1
if (ans != -1)
um[v[i]] += (ans + 1);
}
// Store the answer
int res = 0;
// Traverse the map
for (auto it = um.begin();
it != um.end(); it++) {
// Update the overall answer
res = max(res, n - it->second);
}
// Print the answer
cout << res;
}
// Driver Code
int main()
{
vector > arr
= { { 1, 2 },
{ 3, 4 },
{ 2, 5 } };
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
return 0;
}
Java
// Java program for the above approach
import java.io.*;
import java.lang.*;
import java.util.*;
class GFG
{
// Pair class to store in the um as a key
// with hashcode and equals
static class Pair
{
int first;
int second;
public Pair(int first, int second)
{
this.first = first;
this.second = second;
}
@Override public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + first;
result = prime * result + second;
return result;
}
@Override public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Pair other = (Pair)obj;
if (first != other.first)
return false;
if (second != other.second)
return false;
return true;
}
}
// Function to count maximum number
// of intervals that an interval
// can intersect
static void findMaxIntervals(ArrayList v, int n)
{
// Create a hashmap
HashMap um = new HashMap<>();
// Sort by starting position
Collections.sort(v, (x, y) -> x.first - y.first);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Initalize um for v[i] as 0
um.put(v.get(i), 0);
// Store the starting and
// ending point of the
// ith interval
int start = v.get(i).first;
int end = v.get(i).second;
// Set low and high
int low = i + 1;
int high = n - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to find
// the number of intervals
// completely lying to the
// right of the ith interval
while (low <= high) {
// Find the mid
int mid = low + (high - low) / 2;
// Condition for searching
// in the first half
if (v.get(mid).first > end) {
ans = mid;
high = mid - 1;
}
// Otherwise search in the
// second half
else {
low = mid + 1;
}
}
// Increment um for v[i] by n-ans
// if ans!=-1
if (ans != -1)
um.put(v.get(i), n - ans);
}
// Sort by ending position
Collections.sort(v, (x, y) -> x.second - y.second);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Store the starting and
// ending point of the
// ith interval
int start = v.get(i).first;
int end = v.get(i).second;
// Set low and high
int low = 0;
int high = i - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to
// find the number of intervals
// completely lying to the
// left of the ith interval
while (low <= high) {
int mid = low + (high - low) / 2;
if (v.get(mid).second < start) {
ans = mid;
low = mid + 1;
}
else {
high = mid - 1;
}
}
// Increment um for v[i] by ans+1
// if ans!=-1
if (ans != -1)
um.put(v.get(i),
um.get(v.get(i)) + (ans + 1));
}
// Store the answer
int res = 0;
// Traverse the map
for (int second : um.values()) {
// Update the overall answer
res = Math.max(res, n - second);
}
// Print the answer
System.out.println(res);
}
// Driver Code
public static void main(String[] args)
{
ArrayList arr = new ArrayList<>();
arr.add(new Pair(1, 2));
arr.add(new Pair(3, 4));
arr.add(new Pair(2, 5));
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
}
}
// This code is contributed by Kingash.
3
时间复杂度: O(N 2 )
辅助空间: O(1)
高效方法:可以通过计算不相交的间隔数而不是计算相交数来优化上述方法。不与特定间隔相交的间隔可以分为两个不相交的类别:完全落在左侧或完全落在右侧的间隔。使用此想法,请按照以下步骤解决问题:
- 创建一个哈希表,例如M ,以映射不与每个间隔相交的间隔数。
- 根据起点对间隔进行排序。
- 使用变量i遍历间隔
- 将ans初始化为-1,以存储完全位于第i个间隔右侧的第一个间隔的索引。
- 初始化低和高为第(i + 1)和(N – 1),并执行二进制搜索,如下:
- 找到中间的2值作为(低+高)/。
- 如果interval [mid]的开始位置大于interval [i]的结束位置,则将当前索引mid存储在ans中,然后通过将高位更新为(mid – 1)来检查左半部分。
- 否则,通过将低位更新为(mid + 1)来检入右半部分。
- 如果ans的值不为-1 ,则将(N – ans)添加到M [interval [i]] 。
- 现在,根据结束点对时间间隔进行排序。
- 同样,使用变量i遍历间隔,并应用与上述类似的方法来找到完全位于第i个间隔左侧的间隔。
- 循环之后,遍历映射M并将最小值存储在min中。
- 作为结果打印(N – min)的值。
下面是上述方法的实现:
C++
// C++ program for the above approach
#include
using namespace std;
// Comparator function to sort in
// increasing order of second
// values in each pair
bool compare(pair f,
pair s)
{
return f.second < s.second;
}
// Function to hash a pair
struct hash_pair {
template
size_t operator()(
const pair& p) const
{
auto hash1 = hash{}(p.first);
auto hash2 = hash{}(p.second);
return hash1 ^ hash2;
}
};
// Function to count maximum number
// of intervals that an interval
// can intersect
void findMaxIntervals(
vector > v, int n)
{
// Create a hashmap
unordered_map,
int,
hash_pair>
um;
// Sort by starting position
sort(v.begin(), v.end());
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Initalize um[v[i]] as 0
um[v[i]] = 0;
// Store the starting and
// ending point of the
// ith interval
int start = v[i].first;
int end = v[i].second;
// Set low and high
int low = i + 1;
int high = n - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to find
// the number of intervals
// completely lying to the
// right of the ith interval
while (low <= high) {
// Find the mid
int mid = low + (high - low) / 2;
// Condition for searching
// in the first half
if (v[mid].first > end) {
ans = mid;
high = mid - 1;
}
// Otherwise search in the
// second half
else {
low = mid + 1;
}
}
// Increment um[v[i]] by n-ans
// if ans!=-1
if (ans != -1)
um[v[i]] = n - ans;
}
// Sort by ending position
sort(v.begin(), v.end(), compare);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Store the starting and
// ending point of the
// ith interval
int start = v[i].first;
int end = v[i].second;
// Set low and high
int low = 0;
int high = i - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to
// find the number of intervals
// completely lying to the
// left of the ith interval
while (low <= high) {
int mid = low + (high - low) / 2;
if (v[mid].second < start) {
ans = mid;
low = mid + 1;
}
else {
high = mid - 1;
}
}
// Increment um[v[i]] by ans+1
// if ans!=-1
if (ans != -1)
um[v[i]] += (ans + 1);
}
// Store the answer
int res = 0;
// Traverse the map
for (auto it = um.begin();
it != um.end(); it++) {
// Update the overall answer
res = max(res, n - it->second);
}
// Print the answer
cout << res;
}
// Driver Code
int main()
{
vector > arr
= { { 1, 2 },
{ 3, 4 },
{ 2, 5 } };
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
return 0;
}
Java
// Java program for the above approach
import java.io.*;
import java.lang.*;
import java.util.*;
class GFG
{
// Pair class to store in the um as a key
// with hashcode and equals
static class Pair
{
int first;
int second;
public Pair(int first, int second)
{
this.first = first;
this.second = second;
}
@Override public int hashCode()
{
final int prime = 31;
int result = 1;
result = prime * result + first;
result = prime * result + second;
return result;
}
@Override public boolean equals(Object obj)
{
if (this == obj)
return true;
if (obj == null)
return false;
if (getClass() != obj.getClass())
return false;
Pair other = (Pair)obj;
if (first != other.first)
return false;
if (second != other.second)
return false;
return true;
}
}
// Function to count maximum number
// of intervals that an interval
// can intersect
static void findMaxIntervals(ArrayList v, int n)
{
// Create a hashmap
HashMap um = new HashMap<>();
// Sort by starting position
Collections.sort(v, (x, y) -> x.first - y.first);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Initalize um for v[i] as 0
um.put(v.get(i), 0);
// Store the starting and
// ending point of the
// ith interval
int start = v.get(i).first;
int end = v.get(i).second;
// Set low and high
int low = i + 1;
int high = n - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to find
// the number of intervals
// completely lying to the
// right of the ith interval
while (low <= high) {
// Find the mid
int mid = low + (high - low) / 2;
// Condition for searching
// in the first half
if (v.get(mid).first > end) {
ans = mid;
high = mid - 1;
}
// Otherwise search in the
// second half
else {
low = mid + 1;
}
}
// Increment um for v[i] by n-ans
// if ans!=-1
if (ans != -1)
um.put(v.get(i), n - ans);
}
// Sort by ending position
Collections.sort(v, (x, y) -> x.second - y.second);
// Traverse all the intervals
for (int i = 0; i < n; i++) {
// Store the starting and
// ending point of the
// ith interval
int start = v.get(i).first;
int end = v.get(i).second;
// Set low and high
int low = 0;
int high = i - 1;
// Store the required number
// of intervals
int ans = -1;
// Apply binary search to
// find the number of intervals
// completely lying to the
// left of the ith interval
while (low <= high) {
int mid = low + (high - low) / 2;
if (v.get(mid).second < start) {
ans = mid;
low = mid + 1;
}
else {
high = mid - 1;
}
}
// Increment um for v[i] by ans+1
// if ans!=-1
if (ans != -1)
um.put(v.get(i),
um.get(v.get(i)) + (ans + 1));
}
// Store the answer
int res = 0;
// Traverse the map
for (int second : um.values()) {
// Update the overall answer
res = Math.max(res, n - second);
}
// Print the answer
System.out.println(res);
}
// Driver Code
public static void main(String[] args)
{
ArrayList arr = new ArrayList<>();
arr.add(new Pair(1, 2));
arr.add(new Pair(3, 4));
arr.add(new Pair(2, 5));
int N = arr.size();
// Function Call
findMaxIntervals(arr, N);
}
}
// This code is contributed by Kingash.
3
时间复杂度: O(N * log N)
辅助空间: O(N)