2012-11-13 2 views
4

파일에 대한 사용자 입력을 가져온 프로그램을 만들고 파일 내에서 사용자가 지정하는 문자열을 제거하는 문제를 해결하려고합니다. 내가 가지고있는 것 (아래)에서 질문하는 것에 어떻게 가야할지 모르겠습니다. 언제나처럼 모든 도움이 크게 감사드립니다. io.UnsupportedOperation : 읽을 수 없음

def main(): 
    outfile = open(input("Enter a file name: "), "a") 
    string = input("Enter the string to be removed: ") 
    for string in outfile.readlines(): 
     string = string.replace(string, "") 
    outfile.close() 
    print("Done") 

main() 

나는 제안 중 하나를 가져다가 그 일을 얻기 위해 노력하지만 코드 아래에있는 내 의견에 말했듯이 아래에 빈 파일을 생성 오류를 반환하지 않습니다. 새 파일을 문자열이 제거 된 이전 파일로 가져 오려면 어떻게해야합니까?

def main(): 
    inpath = input("Enter an input file: ") 
    line = input("Enter what you want to remove: ") 
    outpath = input("Enter an output file: ") 
    with open(inpath, "r") as infile, open(outpath, "w") as outfile: 
     for line in infile: 
      outfile.write(line.replace(line, "") + "\n") 
    print("Done.") 

main() 
+5

읽기 모드에서 파일을 열어야합니다. ''a + ''보십시오. – JBernardo

+0

부수적으로'string'이라는 이름의 변수가 너무 많습니다. 당신은 아마도'string1 = input (...)'그리고'string = string.replace (string1, "")'을 원할 것입니다. 마지막으로 실제로 문자열을 파일에 다시 써야합니다. 파일의 문자열을 대체하는 것은 약간 어렵습니다. 일반적으로 수정 된 내용으로 새 파일을 만든 다음 하루가 끝날 때 새 파일을 이전 파일 위로 이동합니다. – mgilson

+0

@JBernardo : 사실이긴하지만 실제로 도움이되지는 않습니다. 파일을 읽는 것을 반복하는 과정에서 파일에 쓸 수는 없지만 다른 플랫폼에서는 불만족 스러울뿐 아니라 불행한 일도 할 수 있습니다. 여전히 출발점이며, OP 제목에 언급 된 오류에 대한 직접적인 설명입니다. – abarnert

답변

8

몇 가지 측면 노트 세부 사항에 들어가기 전에 : string.replace(string, "")를 호출 할 때, 당신이 전체 자체를 대체 할 문자열을 이야기하고있는 빈 문자열 - 당신은뿐만 아니라 단지 string = ""을 할 수 있습니다. 아마도 첫 번째 string은 대체 할 검색 문자열이므로 다른 이름을주고 string.replace(searchString, "")과 같이 사용하십시오. 또한 표준 라이브러리 모듈의 이름이기 때문에 변수 이름을 string으로 지정하고 싶지 않습니다. 입력 파일을 "outfile"이라고 부르면 혼란을 일으킬 수 있습니다. 명시 적 종료 대신 with 문을 사용하려고합니다. 마지막으로 for line in f:을 사용하여 파일의 행을 반복 할 수 있습니다. for line in f.readlines()이 필요하지 않습니다 (파이썬 2.x를 다루어야 할 필요가 있다면 readlines()을 피하는 것이 더 행복 할 것입니다, 왜냐하면 그것은 전체 파일을 메모리에 읽어 들일 것이고 메모리에 많은 라인 목록을 만들 것이기 ​​때문입니다).

JBernardo가 지적한 것처럼 첫 번째 문제는 파일을 "a"모드로 열었습니다.이 모드는 "쓰기 전용, 끝에 추가"를 의미합니다. 읽고 쓰고 싶다면 "a +"또는 "r +"를 사용할 수 있습니다.

그러나 실제로 도움이되지는 않습니다. 결국, 파일을 읽는 중에 파일에 쓸 수 없습니다.

여기에는 몇 가지 일반적인 방법이 있습니다.

먼저 표준 출력에 쓰기 만하면 사용자가 원하는 결과를 출력하도록 할 수 있습니다 (예 : 파일로 리디렉션). (이 경우 프롬프트 대신 "완료"메시지 등을 표준 오류로 출력하여 파일로 리디렉션되지 않습니다.) 이것은 sed 또는 sort과 같은 많은 유닉스 도구가하는 것이므로 적절합니다 유닉스 스타일의 도구를 만들고 있지만 다른 용도로는 적합하지 않을 수도 있습니다.

def stderrinput(prompt): 
    sys.stderr.write(prompt) 
    sys.stderr.flush() 
    return input() 

def main(): 
    with open(stderrinput("Enter a file name: "), "r") as infile: 
     searchString = stderrinput("Enter the string to be removed: ") 
     for line in infile: 
      print(infile.replace(searchString, "")) 
    sys.stderr.write("Done\n") 

두 번째로 다른 파일에 씁니다. "R"모드의 입력 파일 및 "W"모드에서 출력 파일을 열고 다음 방금 복사하는 라인 :

def main(): 
    inpath = input("Enter an input file: ") 
    outpath = input("Enter an output file: ") 
    with open(inpath, "r") as infile, open("outpath", "w") as outfile: 
     for line in infile: 
      outfile.write(line.replace(searchString, "") + "\n") 

셋째, 읽기 및 메모리에 전체 파일을 처리 한 후 잘라 다음,

def main(): 
    path = input("Enter an input/output file: ") 
    with open(path, "r+") as inoutfile: 
     lines = [line.replace(searchString, "") for line in inoutfile] 
     inoutfile.seek(0) 
     inoutfile.truncate() 
     inoutfile.writelines(lines) 

마지막으로, (두 번째 옵션과 마찬가지로) 임시 파일에 쓸 원래의 입력 파일의 맨 위에 그 임시 파일을 이동 : 전체 파일을 다시 작성합니다. 이런 식으로 :

def main(): 
    path = input("Enter an input/output file: ") 
    with open(path, "r") as infile, tempfile.NamedTemporaryFile("w", delete=False) as outfile: 
     for line in infile: 
      outfile.write(line.replace(searchString, "")) 
     shutil.move(outfile.name, pathname) 

이 마지막 것은 POSIX와 Windows의 차이점 때문에 조금 까다 롭습니다. 그러나, 몇 가지 큰 장점이 있습니다. (예를 들어, 프로그램이 작동 중간에 죽게 되더라도 아무리 일이 생기더라도 원본 파일이나 새 파일을 가질 수 있습니다.)

+0

이 루프에서'string = string.replace (string, "")'은 말도 안된다는 것을 주석해야합니다. 두 번째 줄에서, 대체 문자열이 첫 번째 줄입니다. – mgilson

+0

그것은 더욱 악합니다. 두 번째 줄에서 두 번째 줄은 대체 문자열입니다. 모든 행에서 대체 문자열이 현재 행입니다. – abarnert

+0

맞습니다! – mgilson

관련 문제