Largest divisible subset in array
Given an array the task is to largest divisible subset in array. A subset is called divisible if for every pair (x, y) in subset, either x divides y or y divides x.
Examples:
Input : arr[] = {1, 16, 7, 8, 4}
Output : 16 8 4 1
In the output subset, for every pair,
either the first element divides second
or second divides first.
Input : arr[] = {2, 4, 3, 8}
Output : 8 4 2
A simple solution is to generate all subsets of given set. For every generated subset, check if it is divisible or not. Finally print the largest divisible subset.
An efficient solution involves following steps.
- Sort all array elements in increasing order. The purpose of sorting is to make sure that all divisors of an element appear before it.
- Create an array divCount[] of same size as input array. divCount[i] stores size of divisible subset ending with arr[i] (In sorted array). The minimum value of divCount[i] would be 1.
- Traverse all array elements. For every element, find a divisor arr[j] with largest value of divCount[j] and store the value of divCount[i] as divCount[j] + 1.
Implementation:
C++
#include<bits/stdc++.h>
using namespace std;
void findLargest( int arr[], int n)
{
sort(arr, arr+n);
vector < int > divCount(n, 1);
vector < int > prev(n, -1);
int max_ind = 0;
for ( int i=1; i<n; i++)
{
for ( int j=0; j<i; j++)
{
if (arr[i]%arr[j] == 0)
{
if (divCount[i] < divCount[j] + 1)
{
divCount[i] = divCount[j]+1;
prev[i] = j;
}
}
}
if (divCount[max_ind] < divCount[i])
max_ind = i;
}
int k = max_ind;
while (k >= 0)
{
cout << arr[k] << " " ;
k = prev[k];
}
}
int main()
{
int arr[] = {1, 2, 17, 4};
int n = sizeof (arr)/ sizeof ( int );
findLargest(arr, n);
return 0;
}
|
Java
import java.util.*;
class DivSubset {
public static int [][] dp;
static void findLargest( int [] arr) {
int divCount[] = new int [arr.length];
Arrays.fill(divCount, 1 );
int prev[] = new int [arr.length];
Arrays.fill(prev, - 1 );
int max_ind = 0 ;
for ( int i = 1 ; i < arr.length; i++) {
for ( int j = 0 ; j < i; j++) {
if (arr[i] % arr[j] == 0 &&
divCount[i] < divCount[j] + 1 ) {
prev[i] = j;
divCount[i] = divCount[j] + 1 ;
}
}
if (divCount[i] > divCount[max_ind])
max_ind = i;
}
int k = max_ind;
while (k >= 0 ) {
System.out.print(arr[k] + " " );
k = prev[k];
}
}
public static void main(String[] args) {
int [] x = { 1 , 2 , 17 , 4 };
Arrays.sort(x);
findLargest(x);
}
}
|
Python3
def findLargest(arr, n):
arr.sort(reverse = False )
divCount = [ 1 for i in range (n)]
prev = [ - 1 for i in range (n)]
max_ind = 0
for i in range ( 1 ,n):
for j in range (i):
if (arr[i] % arr[j] = = 0 ):
if (divCount[i] < divCount[j] + 1 ):
divCount[i] = divCount[j] + 1
prev[i] = j
if (divCount[max_ind] < divCount[i]):
max_ind = i
k = max_ind
while (k > = 0 ):
print (arr[k],end = " " )
k = prev[k]
if __name__ = = '__main__' :
arr = [ 1 , 2 , 17 , 4 ]
n = len (arr)
findLargest(arr, n)
|
C#
using System;
public class DivSubset
{
public static int [,] dp;
static void findLargest( int [] arr)
{
int []divCount = new int [arr.Length];
for ( int i = 0; i < arr.Length; i++)
divCount[i] = 1;
int []prev = new int [arr.Length];
for ( int i = 0; i < arr.Length; i++)
prev[i] = -1;
int max_ind = 0;
for ( int i = 1; i < arr.Length; i++)
{
for ( int j = 0; j < i; j++)
{
if (arr[i] % arr[j] == 0 &&
divCount[i] < divCount[j] + 1)
{
prev[i] = j;
divCount[i] = divCount[j] + 1;
}
}
if (divCount[i] > divCount[max_ind])
max_ind = i;
}
int k = max_ind;
while (k >= 0)
{
Console.Write(arr[k] + " " );
k = prev[k];
}
}
public static void Main(String[] args)
{
int [] x = { 1, 2, 17, 4};
Array.Sort(x);
findLargest(x);
}
}
|
Javascript
<script>
let dp;
function findLargest(arr)
{
let divCount = new Array(arr.length);
for (let i=0;i<arr.length;i++)
{
divCount[i]=1;
}
let prev = new Array(arr.length);
for (let i=0;i<arr.length;i++)
{
prev[i]=-1;
}
let max_ind = 0;
for (let i = 1; i < arr.length; i++) {
for (let j = 0; j < i; j++) {
if (arr[i] % arr[j] == 0 &&
divCount[i] < divCount[j] + 1) {
prev[i] = j;
divCount[i] = divCount[j] + 1;
}
}
if (divCount[i] > divCount[max_ind])
max_ind = i;
}
let k = max_ind;
while (k >= 0) {
document.write(arr[k] + " " );
k = prev[k];
}
}
let x=[1, 2, 17, 4];
x.sort( function (a,b){ return a-b;});
findLargest(x);
</script>
|
Output:
4 2 1
Time Complexity : O(n2)
Auxiliary Space : O(n)
Last Updated :
13 Sep, 2023
Like Article
Save Article
Share your thoughts in the comments
Please Login to comment...