আমি পাইথন ব্যবহার করছি, এবং ফাইলটি মোছা বা অনুলিপি না করে কোনও পাঠ্য ফাইলে একটি স্ট্রিং toোকাতে চাই। আমি এটা কিভাবে করবো?
আমি পাইথন ব্যবহার করছি, এবং ফাইলটি মোছা বা অনুলিপি না করে কোনও পাঠ্য ফাইলে একটি স্ট্রিং toোকাতে চাই। আমি এটা কিভাবে করবো?
উত্তর:
দুর্ভাগ্যক্রমে কোনও ফাইল পুনরায় না লিখে ofোকানোর কোনও উপায় নেই। পূর্ববর্তী পোস্টারগুলি যেমন ইঙ্গিত করেছে, আপনি কোনও ফাইলের সাথে সংযোজন করতে পারেন বা এর অংশটি ওভাররাইট করে সিক ব্যবহার করে করতে পারেন তবে আপনি যদি শুরুতে বা মাঝখানে স্টাফ যুক্ত করতে চান তবে আপনাকে এটি আবার লিখতে হবে।
এটি একটি অপারেটিং সিস্টেম জিনিস, পাইথন জিনিস নয়। সমস্ত ভাষায় এটি একই রকম।
আমি সাধারণত যা করি তা ফাইল থেকে পড়া, পরিবর্তনগুলি করা এবং এটি মাইফাইল.txt.tmp নামে একটি নতুন ফাইলে লিখুন বা এর মতো কিছু। পুরো ফাইলটি মেমোরিতে পড়ার চেয়ে এটি ভাল কারণ ফাইলটি এর জন্য খুব বড় হতে পারে। অস্থায়ী ফাইলটি শেষ হয়ে গেলে, আমি এটিকে মূল ফাইলের মতোই নতুন নামকরণ করি।
এটি করার একটি দুর্দান্ত, নিরাপদ উপায় কারণ যদি ফাইলটি লেখার কারণে কোনও কারণে ক্র্যাশ হয় বা বন্ধ হয় তবে আপনার কাছে এখনও আপনার অচ্ছুত মূল ফাইলটি রয়েছে।
আপনি যা করতে চান তার উপর নির্ভর করে। সংযোজন করতে আপনি এটি "এ" দিয়ে খুলতে পারেন:
with open("foo.txt", "a") as f:
f.write("new line\n")
আপনি যদি কিছু প্রিপ্রেন্ড করতে চান তবে আপনাকে প্রথমে ফাইলটি পড়তে হবে:
with open("foo.txt", "r+") as f:
old = f.read() # read everything in the file
f.seek(0) # rewind
f.write("new line\n" + old) # write the new line before
with
পাইথন 2.5 তে স্টেটমেন্টটি ব্যবহার করার জন্য আপনাকে সামান্য সংযোজন করতে হবে " ভবিষ্যতের আমদানি সহ_স্টেটমেন্ট" থেকে add এর বাইরে, with
বিবৃতি দিয়ে ফাইলগুলি খোলার বিষয়টি ম্যানুয়াল বন্ধ হওয়ার চেয়ে অবশ্যই বেশি পঠনযোগ্য এবং কম ত্রুটি-প্রবণ one
fileinput
ব্যবহার করার সময় আপনি inline=True
নালাগুলি খোলা / পড়া / পরিবর্তন / লেখার / প্রতিস্থাপনের রুটিনটি হ্যান্ডলগুলি সহ সহায়ক সহায়ক বিবেচনা করতে পারেন । এখানে উদাহরণ: stackoverflow.com/a/2363893/47390
f.Close()
fileinput
পাইথন মান লাইব্রেরির মডিউল একটি ফাইল inplace পুনর্লিখন আপনি inplace = 1 পরামিতি ব্যবহার করব:
import sys
import fileinput
# replace all occurrences of 'sit' with 'SIT' and insert a line after the 5th
for i, line in enumerate(fileinput.input('lorem_ipsum.txt', inplace=1)):
sys.stdout.write(line.replace('sit', 'SIT')) # replace 'sit' and write
if i == 4: sys.stdout.write('\n') # write a blank line after the 5th line
জায়গায় জায়গায় কোনও ফাইল পুনরায় লেখার কাজটি প্রায়শই পুরানো অনুলিপি পরিবর্তিত নামের সাথে সংরক্ষণ করে করা হয়। ইউনিক্স লোকেরা পুরানোটিকে ~
চিহ্নিত করতে একটি যুক্ত করে। উইন্ডোজ লোকেরা সব ধরণের কাজ করে - .bak বা .old - অথবা সম্পূর্ণরূপে ফাইলটির নাম পরিবর্তন করে বা the নামের সামনে রাখে।
import shutil
shutil.move( afile, afile+"~" )
destination= open( aFile, "w" )
source= open( aFile+"~", "r" )
for line in source:
destination.write( line )
if <some condition>:
destination.write( >some additional line> + "\n" )
source.close()
destination.close()
পরিবর্তে shutil
, আপনি নিম্নলিখিত ব্যবহার করতে পারেন।
import os
os.rename( aFile, aFile+"~" )
os.rename(aFile, aFile + "~")
কোনও অনুলিপি তৈরি না করে উত্স ফাইলটির নাম পরিবর্তন করবে।
পাইথনের এমএমএপ মডিউল আপনাকে কোনও ফাইলের মধ্যে প্রবেশ করতে দেবে allow নিম্নলিখিত নমুনাটি ইউনিক্সে এটি কীভাবে করা যায় তা দেখায় (উইন্ডোজ এমএম্যাপটি আলাদা হতে পারে)। নোট করুন যে এটি সমস্ত ত্রুটির শর্তাদি পরিচালনা করে না এবং আপনি মূল ফাইলটি দূষিত বা হারাতে পারেন। এছাড়াও, এটি ইউনিকোড স্ট্রিংগুলি পরিচালনা করবে না।
import os
from mmap import mmap
def insert(filename, str, pos):
if len(str) < 1:
# nothing to insert
return
f = open(filename, 'r+')
m = mmap(f.fileno(), os.path.getsize(filename))
origSize = m.size()
# or this could be an error
if pos > origSize:
pos = origSize
elif pos < 0:
pos = 0
m.resize(origSize + len(str))
m[pos+len(str):] = m[pos:origSize]
m[pos:pos+len(str)] = str
m.close()
f.close()
'আর +' মোডে খোলা ফাইলগুলি এমএমএপ ছাড়াই এটি করাও সম্ভব, তবে আপনাকে সন্নিবেশনের অবস্থান থেকে ইওএফ থেকে সাময়িকভাবে ফাইলের বিষয়বস্তু পড়তে এবং সংরক্ষণ করতে হবে বলে এটি কম সুবিধাজনক এবং কম দক্ষ - যা সম্ভবত বিশাল হতে।
অ্যাডামের উল্লেখ অনুসারে আপনার সিস্টেমের সীমাবদ্ধতাগুলি বিবেচনায় নেওয়ার আগে আপনার কাছে মেমরির সমস্ত অংশ পড়ার মতো পর্যাপ্ত মেমরি রয়েছে কিনা এর অংশগুলি প্রতিস্থাপন করে পুনরায় লিখতে হবে কিনা তা সম্পর্কে সিদ্ধান্ত নেওয়ার আগে।
আপনি যদি একটি ছোট ফাইল নিয়ে কাজ করছেন বা মেমরির সমস্যা না থাকলে এটি সহায়তা করতে পারে:
বিকল্প 1) সম্পূর্ণ ফাইলটিকে মেমোরিতে পড়ুন, লাইনের পুরো বা অংশে একটি রেজেক্স প্রতিস্থাপন করুন এবং সেই লাইনটি অতিরিক্ত লাইন দিয়ে প্রতিস্থাপন করুন। আপনার অবশ্যই নিশ্চিত করতে হবে যে 'মিডল লাইন' ফাইলটিতে অনন্য বা আপনার যদি প্রতিটি লাইনে টাইমস্ট্যাম্প থাকে তবে এটি নির্ভরযোগ্য হওয়া উচিত।
# open file with r+b (allow write and binary mode)
f = open("file.log", 'r+b')
# read entire content of file into memory
f_content = f.read()
# basically match middle line and replace it with itself and the extra line
f_content = re.sub(r'(middle line)', r'\1\nnew line', f_content)
# return pointer to top of file so we can re-write the content with replaced string
f.seek(0)
# clear file content
f.truncate()
# re-write the content with the updated content
f.write(f_content)
# close file
f.close()
বিকল্প 2) মাঝের রেখাটি চিহ্নিত করুন এবং সেই লাইনটি অতিরিক্ত লাইন দিয়ে প্রতিস্থাপন করুন।
# open file with r+b (allow write and binary mode)
f = open("file.log" , 'r+b')
# get array of lines
f_content = f.readlines()
# get middle line
middle_line = len(f_content)/2
# overwrite middle line
f_content[middle_line] += "\nnew line"
# return pointer to top of file so we can re-write the content with replaced string
f.seek(0)
# clear file content
f.truncate()
# re-write the content with the updated content
f.write(''.join(f_content))
# close file
f.close()
পরিষ্কারভাবে এটি করার জন্য একটি ছোট ক্লাস লিখেছিলেন।
import tempfile
class FileModifierError(Exception):
pass
class FileModifier(object):
def __init__(self, fname):
self.__write_dict = {}
self.__filename = fname
self.__tempfile = tempfile.TemporaryFile()
with open(fname, 'rb') as fp:
for line in fp:
self.__tempfile.write(line)
self.__tempfile.seek(0)
def write(self, s, line_number = 'END'):
if line_number != 'END' and not isinstance(line_number, (int, float)):
raise FileModifierError("Line number %s is not a valid number" % line_number)
try:
self.__write_dict[line_number].append(s)
except KeyError:
self.__write_dict[line_number] = [s]
def writeline(self, s, line_number = 'END'):
self.write('%s\n' % s, line_number)
def writelines(self, s, line_number = 'END'):
for ln in s:
self.writeline(s, line_number)
def __popline(self, index, fp):
try:
ilines = self.__write_dict.pop(index)
for line in ilines:
fp.write(line)
except KeyError:
pass
def close(self):
self.__exit__(None, None, None)
def __enter__(self):
return self
def __exit__(self, type, value, traceback):
with open(self.__filename,'w') as fp:
for index, line in enumerate(self.__tempfile.readlines()):
self.__popline(index, fp)
fp.write(line)
for index in sorted(self.__write_dict):
for line in self.__write_dict[index]:
fp.write(line)
self.__tempfile.close()
তারপরে আপনি এটিকে এভাবে ব্যবহার করতে পারেন:
with FileModifier(filename) as fp:
fp.writeline("String 1", 0)
fp.writeline("String 2", 20)
fp.writeline("String 3") # To write at the end of the file
আপনি যদি কিছু ইউনিক্স জানেন তবে আপনি নিম্নলিখিতটি চেষ্টা করতে পারেন:
নোটস: $ মানে কমান্ড প্রম্পট
বলুন যে আপনার কাছে এই জাতীয় সামগ্রীর সাথে একটি ফাইল my_data.txt রয়েছে:
$ cat my_data.txt
This is a data file
with all of my data in it.
তারপরে os
মডিউলটি ব্যবহার করে আপনি সাধারণ sed
কমান্ডগুলি ব্যবহার করতে পারেন
import os
# Identifiers used are:
my_data_file = "my_data.txt"
command = "sed -i 's/all/none/' my_data.txt"
# Execute the command
os.system(command)
আপনি যদি সেড সম্পর্কে সচেতন না হন তবে এটি পরীক্ষা করে দেখুন, এটি অত্যন্ত কার্যকর।