If im not completely misunderstanding your problem and you want a poor way of doing it here it is:
Brute force approach:
- Get P choose (P/N) combos where P is number of elements and N is number of groups you want to partition into.
- Calculate "inner similarity" for each combo returned in 1.
- Get the N least from 2.
Python implementation:
def getValues(matrix):
values=[]
count=1
while ((len(matrix)- count)>0):
j= count
for i in range(len(matrix)- count ):
values.append(matrix[count-1][j ] )
j+=1
count+=1
return values
def c(arr, curr, end,k ,n , comb=[]):
"""get combinations for list length n and choose k elem"""
if comb is None:
comb = []
elif n ==1 :
comb = []
if ((arr.count(1) is not k) and (curr < end)):
tmparr= [ i for i in arr]
tmparr[curr]= 1
c(tmparr, curr+ 1 , end,k ,n + 1 , comb)
tmparr[curr]= 0
c(tmparr, curr+ 1 , end,k ,n + 1 , comb)
if arr.count(1) ==k :
comb.append(arr)
if n is 1:
return comb
def combos(l, choose):
"""
use this w/ c() to get combinations
"""
arr = [1 for i in l]
return c(arr,0 , len(l), choose,1 )
def getComb(combos, elem):
"""
EX. combos=[0,1,1] elem=["A","B","C"]
return ["B","C"]
"""
result= [ ]
for i in combos:
tmp= ""
for j in range(len(i)):
if i[j] is 1:
tmp+= elem[j]
result.append(tmp)
return result
def subSum(sub,d):
"""
EX. sub = "abc" then return value d["ab"]+d["ac"]+d["bc"]
sub -- list of string elements
d -- dictionary
"""
if( len(sub) is 2):
return d[sub[0]+ sub [1]]
sum=0
for i in range(len(sub)-1) :
sum+=d [ sub[0]+ sub [i+1] ]
return sum+ subSum(sub[1:],d)
def contains(a,b):
for i in a:
if i in b:
return True
return False
#**************INPUT HERE**************#
# elements
e = ["A","B", "C", "D", "E", "F"] # partition set into N
N = 2
matrix =[ [100,2,3,4,5,6],
[ 2, 100,9,16,23 ,30] ,
[ 44,22,100,11,5 ,2] ,
[ 11 ,22,33,100, 44, 55],
[1 ,6,7,13,100, 20 ],
[1 ,1,2,3,5,100 ] ]
#**************************************#
if len(matrix) is len(e):
p = getComb(combos(e,(int)(len( matrix)/N)),e)
q = getComb(combos(e,2),e)
values = getValues(matrix)
# make lookup for subSum()
d = {}
for i in range(len(q)):
d[q[i]]=values[i]
result=[]
for i in range(N):
sums = [subSum(i, d) for i in p]
m = min(sums)
s = p[sums.index(m)]
result.append(s)
for i in p:
if contains(s, i):
p.remove(i)
print(result) # this is the answer