将文件读入数组,搜索字符串并返回值

3 投票
1 回答
5829 浏览
提问于 2025-04-16 05:14

好的,我已经在这个问题上纠结了一段时间,还是没搞定。

我正在写一个方法,它接受一个文件名和一个模式。

比如说 findPattern(fname, pat)

我的目标是查找这个模式,比如在文本文件中查找字符串“apple”,然后返回它的位置,格式是[行号, 开始字符索引]。

我刚接触python,听说过很多方法,但要么太复杂,要么我们不被允许使用,比如说索引;我们特别要求使用数组。

我想到了两个嵌套的for循环,外层循环遍历文本文件数组的每个索引,内层循环比较想要的模式的第一个字母。如果找到了,内层循环就会继续检查“apple”中的“p”与文本文件中的字符。

一个主要的问题是我无法把文件内容放入数组中,我只能读取整行。

这是我现在的代码,虽然还不太好用。我只是试着用.tell来查看文件指针的位置,但它总是显示141,我觉得那是文件末尾,但我还没确认。

#.....Id #
#.....Name

#########################
#my intent was for you to write HW3 code as iteration or
#nested iterations that explicitly index the character 
#string as an array; i.e, the Python index() also known as 
#string.index() function is not allowed for this homework.
########################

print
fname = raw_input('Enter filename: ')
pattern = raw_input('Enter pattern: ')

def findPattern(fname, pat):

    f = open(fname, "r")
    for line in f:
        if pat in line:
            print "Found it @ " +(str( f.tell()))
            break
    else:
        print "No esta..."    

print findPattern(fname, pattern)

编辑:

fname = raw_input('Enter filename: ')
pattern = raw_input('Enter pattern: ')

def findPattern(fname, pat):

    arr = array.array('c', open(fname, 'rb').read())

    for i in xrange(len(arr)):
        if ''.join(arr[i:i+len(pat)]) == pat:
            print 'Found @ %d' % i    

print

findPattern(fname, pattern)

从上面替换的新代码来看,我得到了下面的结果。我知道这可能是数组没有声明之类的简单问题,但我不太确定python的语法,声明数组时不需要设置大小吗?

lynx:desktop $ python hw3.py

Enter filename: declaration.txt
Enter pattern: become

Traceback (most recent call last):
  File "hw3.py", line 25, in <module>
    findPattern(fname, pattern)
  File "hw3.py", line 17, in findPattern
    arr = array.array('c', open(fname, 'rb').read())
NameError: global name 'array' is not defined

编辑:完成了!谢谢大家。这是我搞定它的方法……

#Iterate through
for i in xrange(len(arr)):

    #Check for endline to increment linePos
    if arr[i] == '\n':
        linePos = linePos + 1
        colPos = i

    #Compare a chunk of array the same size
    #as pat with pat itself
    if ''.join(arr[i:i+len(pat)]) == pat:

        #Account for newline with absolute position
        resultPos = i - colPos
        print 'Found @ %d on line %d' % (resultPos, linePos)

1 个回答

1

把文本数据放进数组里,唯一的方法就是把它变成字符:

a = array.array('c', open(filename, 'rb').read())

接下来,你可以简单地遍历这个字符数组,把每个和你要比较的子串长度相同的小数组转换成字符串,然后进行比较:

for i in xrange(len(a)):
   if ''.join(a[i:i+len(substring)]) == substring:
      print 'Found @ %d!' % i

不过,这种做法在Python中并不优雅,而且非常慢

如果你说的数组其实是指列表(在Python中这两个词的意思差别很大):

pos = 0
for line in open(filename):
    for i in xrange(len(line)):
        if line[i:i+len(substring)] == substring:
           print 'Found @ %d!' % (pos + i)
    pos += len(line) + 2 # 1 if on Linux

这种方法也慢而且不够优雅,但比之前的方法稍微好一点。如果这些真的是你被要求做的事情,那你的老师可能不太适合教Python。:p

撰写回答