Python 从论文作者列表中计算一个鄂尔多斯数字
埃尔德的数字描述了一个人和数学家保罗·埃尔德之间的“合作距离”,这是由数学论文的作者来衡量的。要分配Erdős编号,必须有人与另一个Erdős编号有限的人共同撰写研究论文。Paul Erdős的Erdős数为零。任何其他人的Erdős数为k+1,其中k是任何合著者的最低Erdős数 给定一份作者(和论文)列表,我想为每一组作者生成一个Erdős编号。源数据如下(来自input.txt文件): 计算Erdős数的作者有:Python 从论文作者列表中计算一个鄂尔多斯数字,python,python-2.7,Python,Python 2.7,埃尔德的数字描述了一个人和数学家保罗·埃尔德之间的“合作距离”,这是由数学论文的作者来衡量的。要分配Erdős编号,必须有人与另一个Erdős编号有限的人共同撰写研究论文。Paul Erdős的Erdős数为零。任何其他人的Erdős数为k+1,其中k是任何合著者的最低Erdős数 给定一份作者(和论文)列表,我想为每一组作者生成一个Erdős编号。源数据如下(来自input.txt文件): 计算Erdős数的作者有: Smith, M.N. Hsueh, Z. Chen, X. 我目前的计划
Smith, M.N.
Hsueh, Z.
Chen, X.
我目前的计划是从每个条目中删除姓名,并形成一个姓名列表(或列表)。但我不确定这样做的最佳方式。我应该用什么?努比?阅读线
更新:
输出应如下所示:
Scenario 1
Smith, M.N. 1
Hsueh, Z. infinity
Chen, X. 2
我已经提交了对你的问题的编辑,试图澄清你希望实现的目标。基于此,我编写了以下代码来回答我认为您要问的问题:
f = ['Smith, M.N., Martin, G., Erdos, P.: Newtonian forms of prime factors',
'Erdos, P., Reisig, W.: Stuttering in petri nets',
'Smith, M.N., Chen, X.: First order derivates in structured programming',
'Jablonski, T., Hsueh, Z.: Selfstabilizing data structures']
author_en = {} # Dict to hold scores/author
coauthors = []
targets = ['Smith, M.N.','Hsueh, Z.','Chen, X.']
for line in f:
# Split the line on the :
authortext,papers = line.split(':')
# Split on comma, then rejoin author (every 2)
# See: http://stackoverflow.com/questions/9366650/string-splitting-after-every-other-comma-in-string-in-python
authors = authortext.split(', ')
authors = map(', '.join, zip(authors[::2], authors[1::2]))
# Authors now contains a list of authors names
coauthors.append( authors )
for author in authors:
author_en[ author ] = None
author_en['Erdos, P.'] = 0 # Special case
现在我们有了一个列表:每个列表都包含给定出版物的合著者和保存分数的dict。我们需要反复阅读每篇论文,并给作者打分。我不完全清楚鄂尔多斯分数的计算方法,但你可能想循环分数分配,直到没有变化为止——以解释影响早期分数的后期论文
for ca in coauthors:
minima = None
for a in ca:
if author_en[a] != None and ( author_en[a]<minima or minima is None ): # We have a score
minima = author_en[a]
if minima != None:
for a in ca:
if author_en[a] == None:
author_en[a] = minima+1 # Lowest score of co-authors + 1
for author in targets:
print "%s: %s" % ( author, author_en[author] )
联合作者中的ca的:
最小值=无
对于ca中的a:
如果作者_en[a]!=None和(作者_en[a]为了更好地理解这个问题,请注意,基本上这是公正的,可以使用。
问题中的图形定义为:
每个节点代表一个作者
两个节点之间有一条边,如果有一篇论文,由两个节点代表的两位作者共同撰写
对于您的示例,图表如下所示:
Reisig
|
|
Erdos -- Martin
| /
| /
| /
| /
| /
Smith -- Chen
Jablonski -- Hsueh
其中输入:
1
4 3
Smith, M.N., Martin, G., Erdos, P.: Newtonian forms of prime factors
Erdos, P., Reisig, W.: Stuttering in petri nets
Smith, M.N., Chen, X.: First order derivates in structured programming
Jablonski, T., Hsueh, Z.: Selfstabilizing data structures
Smith, M.N.
Hsueh, Z.
Chen, X.
1.
4 3
史密斯,M.N.,马丁,G.,鄂尔多斯,P.:素因子的牛顿形式
Erdos,P.,Reisig,W.:petri网中的口吃
Smith,M.N.,Chen,X.:结构化编程中的一阶导数
贾布隆斯基,T.,薛,Z.:自稳定数据结构
史密斯,M.N。
薛,Z。
陈,X。
将输出:
Scenario 1
Smith, M.N. 1
Hsueh, Z. infinity
Chen, X. 2
情景1
史密斯,M.N.1
薛,Z。无限
陈,X.2
注:
更一般的问题可以描述为,最简单的解决方案就是使用它。如果有人在寻找Java实现:
import java.util.*;
public class P10044 {
public static void main(String[] args) {
Scanner c = new Scanner(System.in);
int cases = c.nextInt();
for (int currentCase = 1; currentCase<=cases; currentCase++) {
int p = c.nextInt();
int n = c.nextInt();
c.nextLine();
HashMap<String, ArrayList<String>> graph = new HashMap<>();
String[] testingNames = new String[n];
ArrayList<String> authors = new ArrayList<>();
HashMap<String, Integer> eNums = new HashMap<>();
while (p-- > 0) {
String[] paperAuthors = c.nextLine().split(":")[0].split("\\.,");
for (int i = 0; i < paperAuthors.length; i++) {
if (paperAuthors[i].charAt(paperAuthors[i].length() - 1) != '.')
paperAuthors[i] += '.';
paperAuthors[i] = paperAuthors[i].trim();
}
for (String author : paperAuthors)
if (!authors.contains(author))
authors.add(author);
// create and update the graph
for (String name : paperAuthors) {
ArrayList<String> updatedValue;
if (graph.keySet().contains(name))
updatedValue = graph.get(name);
else
updatedValue = new ArrayList<>();
for (String paperAuthor : paperAuthors)
if (!paperAuthor.equals(name))
updatedValue.add(paperAuthor);
graph.put(name, updatedValue);
}
}
//initialize the eNums map:
for (String author : authors)
if (!author.equals("Erdos, P."))
eNums.put(author, Integer.MAX_VALUE);
else
eNums.put(author, 0);
for (int i = 0; i < n; i++)
testingNames[i] = c.nextLine();
calculateEnums("Erdos, P.", graph, eNums);
System.out.println("Scenario " + currentCase);
for (String name : testingNames)
if (!eNums.keySet().contains(name) || eNums.get(name) == Integer.MAX_VALUE)
System.out.println(name + " infinity");
else
System.out.println(name + " " + eNums.get(name));
}
}
private static void calculateEnums(String name, HashMap<String, ArrayList<String>> graph,
HashMap<String, Integer> eNums) {
ArrayList<String> notCalculated = new ArrayList<>();
notCalculated.add(name);
while (notCalculated.size() > 0) {
String currentName = notCalculated.get(0);
for (String connectedName : graph.get(currentName)) {
if (eNums.get(connectedName) > eNums.get(currentName)) {
eNums.put(connectedName, eNums.get(currentName) + 1);
if(!notCalculated.contains(connectedName))
notCalculated.add(connectedName);
}
}
notCalculated.remove(0);
}
// recursive implementation but will result in TLE
// for(String connected: graph.get(name)) {
// if (eNums.get(connected) > eNums.get(name)) {
// eNums.put(connected, eNums.get(name) + 1);
// calculateEnums(connected, graph, eNums);
// }
// }
}
}
import java.util.*;
公共类P10044{
公共静态void main(字符串[]args){
扫描仪c=新扫描仪(System.in);
int cases=c.nextInt();
对于(int currentCase=1;currentCase 0){
字符串[]paperAuthors=c.nextLine().split(“:”[0]。split(“\\”);
对于(int i=0;i0){
字符串currentName=notCalculated.get(0);
for(字符串connectedName:graph.get(currentName)){
if(eNums.get(connectedName)>eNums.get(currentName)){
eNums.put(connectedName,eNums.get(currentName)+1);
如果(!notCalculated.contains(connectedName))
未计算。添加(connectedName);
}
}
未计算。删除(0);
}
//递归实现,但会导致TLE
//for(字符串连接:graph.get(name)){
//if(eNums.get(connected)>eNums.get(name)){
//eNums.put(已连接,eNums.get(name)+1);
//计算(连接、图形、枚举);
// }
// }
}
}
您是否可以使用报价和/或代码功能,以便我们查看示例输入的格式?并描述您希望输出的内容(“检查列表”?)通过为您的示例输入提供所需的结果而看起来像是什么?同时,您可能不想在此处使用readline
。对于文件中的行:
循环通常比循环更容易,而True:
line=file.readline()
如果不是行:中断
循环。但是手动读取文件并解析每条记录(使用
1
4 3
Smith, M.N., Martin, G., Erdos, P.: Newtonian forms of prime factors
Erdos, P., Reisig, W.: Stuttering in petri nets
Smith, M.N., Chen, X.: First order derivates in structured programming
Jablonski, T., Hsueh, Z.: Selfstabilizing data structures
Smith, M.N.
Hsueh, Z.
Chen, X.
Scenario 1
Smith, M.N. 1
Hsueh, Z. infinity
Chen, X. 2
import java.util.*;
public class P10044 {
public static void main(String[] args) {
Scanner c = new Scanner(System.in);
int cases = c.nextInt();
for (int currentCase = 1; currentCase<=cases; currentCase++) {
int p = c.nextInt();
int n = c.nextInt();
c.nextLine();
HashMap<String, ArrayList<String>> graph = new HashMap<>();
String[] testingNames = new String[n];
ArrayList<String> authors = new ArrayList<>();
HashMap<String, Integer> eNums = new HashMap<>();
while (p-- > 0) {
String[] paperAuthors = c.nextLine().split(":")[0].split("\\.,");
for (int i = 0; i < paperAuthors.length; i++) {
if (paperAuthors[i].charAt(paperAuthors[i].length() - 1) != '.')
paperAuthors[i] += '.';
paperAuthors[i] = paperAuthors[i].trim();
}
for (String author : paperAuthors)
if (!authors.contains(author))
authors.add(author);
// create and update the graph
for (String name : paperAuthors) {
ArrayList<String> updatedValue;
if (graph.keySet().contains(name))
updatedValue = graph.get(name);
else
updatedValue = new ArrayList<>();
for (String paperAuthor : paperAuthors)
if (!paperAuthor.equals(name))
updatedValue.add(paperAuthor);
graph.put(name, updatedValue);
}
}
//initialize the eNums map:
for (String author : authors)
if (!author.equals("Erdos, P."))
eNums.put(author, Integer.MAX_VALUE);
else
eNums.put(author, 0);
for (int i = 0; i < n; i++)
testingNames[i] = c.nextLine();
calculateEnums("Erdos, P.", graph, eNums);
System.out.println("Scenario " + currentCase);
for (String name : testingNames)
if (!eNums.keySet().contains(name) || eNums.get(name) == Integer.MAX_VALUE)
System.out.println(name + " infinity");
else
System.out.println(name + " " + eNums.get(name));
}
}
private static void calculateEnums(String name, HashMap<String, ArrayList<String>> graph,
HashMap<String, Integer> eNums) {
ArrayList<String> notCalculated = new ArrayList<>();
notCalculated.add(name);
while (notCalculated.size() > 0) {
String currentName = notCalculated.get(0);
for (String connectedName : graph.get(currentName)) {
if (eNums.get(connectedName) > eNums.get(currentName)) {
eNums.put(connectedName, eNums.get(currentName) + 1);
if(!notCalculated.contains(connectedName))
notCalculated.add(connectedName);
}
}
notCalculated.remove(0);
}
// recursive implementation but will result in TLE
// for(String connected: graph.get(name)) {
// if (eNums.get(connected) > eNums.get(name)) {
// eNums.put(connected, eNums.get(name) + 1);
// calculateEnums(connected, graph, eNums);
// }
// }
}
}