检测重复项
Detect duplicates
我的问题是关于检测重复项。假设我有以下数据:
clear all
input str2 pos str10 name
A Joe
A Joe
B Frank
C Mike
C Ted
D Mike
D Mike
E Bill
F Bill
end
如果我想检测所有重复的名字,我只需输入:
duplicates tag name, gen(flag)
这给了我:
pos name flag
A Joe 1
A Joe 1
B Frank 0
C Mike 2
C Ted 0
D Mike 2
D Mike 2
E Bill 1
F Bill 1
太好了 - 它表明 Joe
、Mike
和 Bill
是重复的。
但是假设我不想包含任何仅在 pos
中重复的重复项。换句话说,我不想发现 Joe
是重复的,因为 Joe 只出现在 pos
A
中。我只想发现 Mike
和 Bill
是重复的。 (虽然 Mike
在 D
中重复出现,但他也出现在 C
中,因此他出现在多个 pos
中。)
换句话说,我想要:
pos name flag
A Joe 0
A Joe 0
B Frank 0
C Mike 1
C Ted 0
D Mike 1
D Mike 1
E Bill 1
F Bill 1
请注意,此处 Mike
只取 flag
而不是 1
而不是 2
。那是因为我将 D
中的 Mike
视为只出现一次而不是两次。如果解决方案产生这个问题,那么使用 2
而不是 1
是没有问题的。
有办法吗?
这不再是duplicates
特定意义上的重复问题。 (免责声明:我最初写的。)
您只想知道给定名称是否出现在不同的组中。这个问题在很多地方都有评论,比如here。
一种继续进行的方法是标记 name
和 pos
的每个不同的联合出现仅一次,然后对组进行计数。
clear
input str1 pos str5 name flag
A Joe 1
A Joe 1
B Frank 0
C Mike 2
C Ted 0
D Mike 2
D Mike 2
E Bill 1
F Bill 1
end
egen tag = tag(name pos)
egen npos = total(tag), by(name)
list , sepby(pos)
+---------------------------------+
| pos name flag tag npos |
|---------------------------------|
1. | A Joe 1 1 1 |
2. | A Joe 1 0 1 |
|---------------------------------|
3. | B Frank 0 1 1 |
|---------------------------------|
4. | C Mike 2 1 2 |
5. | C Ted 0 1 1 |
|---------------------------------|
6. | D Mike 2 1 2 |
7. | D Mike 2 0 2 |
|---------------------------------|
8. | E Bill 1 1 2 |
|---------------------------------|
9. | F Bill 1 1 2 |
+---------------------------------+
有些人可能希望看到没有 egen
的解决方案:
bysort name pos: gen tag = _n == 1
by name: gen npos = sum(tag)
by name replace npos = npos[_N]
这可以只使用一个新变量重写:
bysort name pos: gen npos = _n == 1
by name: replace npos = sum(npos)
by name: replace npos = npos[_N]
我的问题是关于检测重复项。假设我有以下数据:
clear all
input str2 pos str10 name
A Joe
A Joe
B Frank
C Mike
C Ted
D Mike
D Mike
E Bill
F Bill
end
如果我想检测所有重复的名字,我只需输入:
duplicates tag name, gen(flag)
这给了我:
pos name flag
A Joe 1
A Joe 1
B Frank 0
C Mike 2
C Ted 0
D Mike 2
D Mike 2
E Bill 1
F Bill 1
太好了 - 它表明 Joe
、Mike
和 Bill
是重复的。
但是假设我不想包含任何仅在 pos
中重复的重复项。换句话说,我不想发现 Joe
是重复的,因为 Joe 只出现在 pos
A
中。我只想发现 Mike
和 Bill
是重复的。 (虽然 Mike
在 D
中重复出现,但他也出现在 C
中,因此他出现在多个 pos
中。)
换句话说,我想要:
pos name flag
A Joe 0
A Joe 0
B Frank 0
C Mike 1
C Ted 0
D Mike 1
D Mike 1
E Bill 1
F Bill 1
请注意,此处 Mike
只取 flag
而不是 1
而不是 2
。那是因为我将 D
中的 Mike
视为只出现一次而不是两次。如果解决方案产生这个问题,那么使用 2
而不是 1
是没有问题的。
有办法吗?
这不再是duplicates
特定意义上的重复问题。 (免责声明:我最初写的。)
您只想知道给定名称是否出现在不同的组中。这个问题在很多地方都有评论,比如here。
一种继续进行的方法是标记 name
和 pos
的每个不同的联合出现仅一次,然后对组进行计数。
clear
input str1 pos str5 name flag
A Joe 1
A Joe 1
B Frank 0
C Mike 2
C Ted 0
D Mike 2
D Mike 2
E Bill 1
F Bill 1
end
egen tag = tag(name pos)
egen npos = total(tag), by(name)
list , sepby(pos)
+---------------------------------+
| pos name flag tag npos |
|---------------------------------|
1. | A Joe 1 1 1 |
2. | A Joe 1 0 1 |
|---------------------------------|
3. | B Frank 0 1 1 |
|---------------------------------|
4. | C Mike 2 1 2 |
5. | C Ted 0 1 1 |
|---------------------------------|
6. | D Mike 2 1 2 |
7. | D Mike 2 0 2 |
|---------------------------------|
8. | E Bill 1 1 2 |
|---------------------------------|
9. | F Bill 1 1 2 |
+---------------------------------+
有些人可能希望看到没有 egen
的解决方案:
bysort name pos: gen tag = _n == 1
by name: gen npos = sum(tag)
by name replace npos = npos[_N]
这可以只使用一个新变量重写:
bysort name pos: gen npos = _n == 1
by name: replace npos = sum(npos)
by name: replace npos = npos[_N]