我如何找到元素的每个组合
How do I find every combination of elements
我有一个元素列表:
John
Richard
Bill
Bob
Walter
而且我想做一些事情来将它们的所有可能组合放在两列中,不包括重复项。这是示例:
A B
John Richard
John Bill
John Bob
John Walter
Richard Bill
Richard Bob
Richard Walter
Bill Bob
Bill Walter
Bob Walter
如您所见,我排除了 John-John 和 Walter-Bill,因为已经有 Bill-Walter 组合。我如何使用公式来做到这一点?
这是我的方法:
function myFunction() {
var names = ['John', 'Richard', 'Bill', 'Bob', 'Walter'];
var result = []
var sheet = SpreadsheetApp.getActive().getSheetByName("sheet1")
names.forEach( (element, index) => {
names.slice(index+1,names.length).forEach ( (rest) => {
result.push([element,rest])
})})
sheet.getRange(2,1,result.length,result[0].length).setValues(result);
}
解释:
本质上,您是在遍历名称列表。从每个元素开始,您只连接下一个元素。例如,John 是名称列表中的第一个元素,您将 John 与 Richard 连接起来,Bill、Bob 和 Walter。然后转到下一个元素 Richard 并将他与 Bill、Bob 和 沃尔特。
通过这种方式,您可以避免重复:John - John 或 John - Richard 和 Richard - John. forEach 方法可帮助您实现这种迭代方法。
References:
How do I do that using formulas?
使用:
=ARRAYFORMULA(SORT(UNIQUE(QUERY(IF(
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9)))>
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9))), {
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9))),
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9)))}, {
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9))),
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9)))}),
"where Col1<>Col2", 0))))
如果A1:A5包含姓名,
=ARRAYFORMULA(SPLIT(QUERY(
FLATTEN(
IF(SEQUENCE(COUNTA(A1:A5))<TRANSPOSE(SEQUENCE(COUNTA(A1:A5))),
A1:A5& "☤" & TRANSPOSE(A1:A5)
,)
),
"where Col1 is not null",0),"☤"))
SEQUENCE(5)<TRANSPOSE(SEQUENCE(5)
创建一个“真正的”上三角(对角线为 0)二维矩阵
0 1 1 1 1
0 0 1 1 1
0 0 0 1 1
0 0 0 0 1
0 0 0 0 0
- 使用
IF
将 2D 矩阵转换为 CONCATEnated 名称:
John☤Rich John☤Bill John☤Bob John☤Walt
Rich☤Bill Rich☤Bob Rich☤Walt
Bill☤Bob Bill☤Walt
Bob☤Walt
FLATTEN
矩阵,使用 QUERY
和 SPLIT
后面的串联名称删除空格
我有一个元素列表:
John
Richard
Bill
Bob
Walter
而且我想做一些事情来将它们的所有可能组合放在两列中,不包括重复项。这是示例:
A B
John Richard
John Bill
John Bob
John Walter
Richard Bill
Richard Bob
Richard Walter
Bill Bob
Bill Walter
Bob Walter
如您所见,我排除了 John-John 和 Walter-Bill,因为已经有 Bill-Walter 组合。我如何使用公式来做到这一点?
这是我的方法:
function myFunction() {
var names = ['John', 'Richard', 'Bill', 'Bob', 'Walter'];
var result = []
var sheet = SpreadsheetApp.getActive().getSheetByName("sheet1")
names.forEach( (element, index) => {
names.slice(index+1,names.length).forEach ( (rest) => {
result.push([element,rest])
})})
sheet.getRange(2,1,result.length,result[0].length).setValues(result);
}
解释:
本质上,您是在遍历名称列表。从每个元素开始,您只连接下一个元素。例如,John 是名称列表中的第一个元素,您将 John 与 Richard 连接起来,Bill、Bob 和 Walter。然后转到下一个元素 Richard 并将他与 Bill、Bob 和 沃尔特。 通过这种方式,您可以避免重复:John - John 或 John - Richard 和 Richard - John. forEach 方法可帮助您实现这种迭代方法。
References:
How do I do that using formulas?
使用:
=ARRAYFORMULA(SORT(UNIQUE(QUERY(IF(
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9)))>
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9))), {
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9))),
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9)))}, {
TRANSPOSE(SPLIT(CONCATENATE(REPT(A1:A&CHAR(9), COUNTA(A1:A))), CHAR(9))),
TRANSPOSE(SPLIT(REPT(CONCATENATE(A1:A&CHAR(9)), COUNTA(A1:A)), CHAR(9)))}),
"where Col1<>Col2", 0))))
如果A1:A5包含姓名,
=ARRAYFORMULA(SPLIT(QUERY(
FLATTEN(
IF(SEQUENCE(COUNTA(A1:A5))<TRANSPOSE(SEQUENCE(COUNTA(A1:A5))),
A1:A5& "☤" & TRANSPOSE(A1:A5)
,)
),
"where Col1 is not null",0),"☤"))
SEQUENCE(5)<TRANSPOSE(SEQUENCE(5)
创建一个“真正的”上三角(对角线为 0)二维矩阵
0 1 1 1 1
0 0 1 1 1
0 0 0 1 1
0 0 0 0 1
0 0 0 0 0
- 使用
IF
将 2D 矩阵转换为 CONCATEnated 名称:
John☤Rich John☤Bill John☤Bob John☤Walt
Rich☤Bill Rich☤Bob Rich☤Walt
Bill☤Bob Bill☤Walt
Bob☤Walt
FLATTEN
矩阵,使用QUERY
和SPLIT
后面的串联名称删除空格