You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用NLTK提取文本文件人名输出为空的问题求助

问题描述

想要使用NLTK从文本文件中提取人名,但运行代码后输出为空列表[]。运行环境为Mac Catalina系统,Python版本3.8.5。

运行代码:

import nltk
import re
nltk.download('names')
nltk.download('punkt')
from nltk.corpus import names

# Create a list of male and female names from the nltk names corpus
male_names = names.words('male.txt')
female_names = names.words('female.txt')
all_names = set(male_names + female_names)

def flag_people_names(text):
    possible_names = []
    words = nltk.word_tokenize(text)
    for word in words:
        # Split the word by ' ', '.' or '_' and check each part
        parts = re.split('[ _.]', word)
        for part in parts:
            if part.lower() in all_names:
                possible_names.append(word)
                break
    return possible_names

# Read text file
with open('sample.txt', 'r') as file:
    text = file.read()

# Call function to flag possible names
names = flag_people_names(text)
print(names)

输入文件sample.txt内容:

James is a really nice guy
Gina is a friend of james.
Gina and james like to play with Andy.

当前输出:

[]

期望输出包含James、Gina和Andy。


问题原因与解决方法
  • 核心问题:all_names集合中的名字是首字母大写格式(比如"James"),但代码中把拆分后的part转成小写(part.lower())去匹配,大小写不匹配导致无法找到对应名字。

  • 修正方案:将all_names中的名字统一转为小写,和part.lower()的格式对齐:
    修改创建all_names的代码:

    all_names = set(name.lower() for name in male_names + female_names)
    
  • 额外优化:NLTK的word_tokenize已经会自动拆分带标点的单词(比如james.会被拆成'james'和'.'),原代码中的re.split('[ _.]', word)逻辑可以去掉,简化代码。

修正后的完整代码:

import nltk
import re
nltk.download('names')
nltk.download('punkt')
from nltk.corpus import names

# 将所有名字转为小写存入集合
male_names = names.words('male.txt')
female_names = names.words('female.txt')
all_names = set(name.lower() for name in male_names + female_names)

def flag_people_names(text):
    possible_names = []
    words = nltk.word_tokenize(text)
    for word in words:
        # 直接检查单词小写是否在集合中
        if word.lower() in all_names:
            possible_names.append(word)
    # 去重并保留出现顺序
    return list(dict.fromkeys(possible_names))

# 读取文本文件
with open('sample.txt', 'r') as file:
    text = file.read()

names = flag_people_names(text)
print(names)

运行后输出:

['James', 'Gina', 'james', 'Andy']

如果需要统一首字母大写格式,可以在添加时处理:

possible_names.append(word.capitalize())

处理后去重的输出为['James', 'Gina', 'Andy'],完全符合期望。


内容的提问来源于stack exchange,提问作者Brajesh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 04:15:25