English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية
이 글은 다음과 같은 몇 가지 방면에서 하나씩 해결할 것입니다.
1프로그램의 주요 기능
2구현 과정
3클래스 정의
4generator를 사용하여 각 객체를 동적으로 업데이트하고 객체를 반환합니다.
5unnecessary characters를 제거하기 위해 strip를 사용합니다.
6rematch를 사용하여 문자열을 일치시킵니다.
7timestrptime를 사용하여 문자열을 시간 객체로 변환합니다.
8、전체 코드
프로그램의 주요 기능
현재 사용자 정보를 저장하는 테이블과 같은 문서가 있습니다. 첫 번째 행은 속성이며, 각 속성은 콤마(,)로 구분되어 있습니다. 두 번째 행부터 각 행은 각 속성에 해당하는 값을 가지고 있으며, 각 행은 하나의 사용자를 대표합니다. 이 문서를 읽어들이고, 각 행을 하나의 사용자 객체로 출력하는 방법을 어떻게 구현할 수 있을까요?
또한4개의 요구사항
각 문서는 매우 크며, 모든 행이 생성된 많은 객체를 한 번에 리스트로 저장하면 메모리가 터질 수 있습니다. 프로그램은 각 행이 생성된 객체를 매번 저장해야 합니다.
구분된 각 문자열은, 앞뒤에 두 개의 쌍따옴표(”)나 단따옴표(')가 있을 수 있습니다. 예를 들어, "张三". 따옴표를 제거합니다; 숫자라면+000000001.24이런 것을 추출해야 합니다.+0을 모두 제거하고,1.24
문서에 시간이 있을 수 있습니다. 형식은 다음과 같습니다:2013-10-29또는2013/10/29 2:23:56 이런 형식으로, 이런 문자열을 시간 유형으로 변환해야 합니다.
이러한 문서는 많이 있습니다. 각 문서의 속성은 다릅니다. 예를 들어, 이는 사용자 정보입니다. 그리고 다른 것은 통화 기록입니다. 따라서 클래스의 구체적인 속성은 문서의 첫 번째 행에 따라 동적으로 생성되어야 합니다.
구현 과정
1. 클래스 정의
속성이 동적으로 추가되기 때문에 속성-값 쌍도 동적으로 추가됩니다. 클래스에 updateAttributes()와 updatePairs() 두 개의 멤버 함수가 있어야 하며, attributes 리스트를 사용하여 속성을 저장하고, attrilist 딕셔너리를 사용하여 매핑을 저장합니다. 또한 init() 함수는 생성자입니다. __attributes 앞에 밑줄이 있으면 private 변수를 의미하며, 바깥에서 직접 호출할 수 없습니다. 인스턴스화할 때는 단순히 a=UserInfo()만으로도 됩니다. 추가적인 매개변수는 필요하지 않습니다.
class UserInfo(object): 'Class to restore UserInformation' def __init__ (self): self.attrilist={} self.__attributes=[] def updateAttributes(self,attributes): self.__attributes=attributes def updatePairs(self,values): for i in range(len(values)): self.attrilist[self.__attributes[i]]=values[i]
2. generator로 각 객체를 동적으로 업데이트하고 객체를 반환
generator는 초기화를 한 번만 하면 자동으로 여러 번 실행할 수 있는 함수입니다. 각 번째 루프마다 하나의 결과를 반환합니다. 하지만 함수는 return으로 결과를 반환하지만, generator는 yield로 결과를 반환합니다. 각 번째 실행은 yield에서 시작하며, 다음 실행은 yield 다음부터 시작합니다. 예를 들어, 우리는 피보나치 수열을 함수와 generator로 구현합니다:
def fib(max): n, a, b = 0, 0, 1 while n < max: print(b) a, b = b, a + b n = n + 1 return 'done'
우리는 수열의 앞6개수:
>>> fib(6) 1 1 2 3 5 8 'done'
generator를 사용할 경우, print을 yield로 변경하면 됩니다. 예를 들어:
def fib(max): n, a, b = 0, 0, 1 while n < max: yield b a, b = b, a + b n = n + 1
사용 방법:
>>> f = fib(6) >>> f <generator object fib at 0x104feaaa0> >>> for i in f: ... print(i) ... 1 1 2 3 5 8 >>>
fib는 생성자로서 객체입니다. yield에 도달하면 중단되어 결과를 반환하고, 다음 번에는 yield 다음의 코드에서부터 계속 실행됩니다. 생성자는 generator.next()를 사용하여 실행할 수도 있습니다.
내 프로그램에서 생성자 부분 코드는 다음과 같습니다:
def ObjectGenerator(maxlinenum): filename='/홈/thinkit/문서/usr_info/USER.csv attributes=[] linenum=1 a=UserInfo() file=open(filename) while linenum < maxlinenum : values=[] line=str.decode(file.readline(),'gb2312)#linecache.getline(filename, linenum,'gb2312) if line=='': print'reading fail! Please check filename!' break str_list=line.split(',') for item in str_list : item=item.strip() item=item.strip('\"') item=item.strip('\'') item=item.strip('+0*) item=catchTime(item) if linenum==1: attributes.append(item) else : values.append(item) if linenum==1: a.updateAttributes(attributes) else : a.updatePairs(values) yield a.attrilist # 'a'를 사용하려면 ' '으로 변경 linenum = linenum +1
a=UserInfo()는 UserInfo 클래스의 인스턴스입니다. 문서는 gb2312인코딩된 것입니다. 위에서는 해당 디코딩 메서드를 사용했습니다. 첫 번째 행은 속성이며, UserInfo에 속성 목록을 저장하는 함수가 있습니다. 즉, updateAttributes(); 다음 행은 속성을 저장해야 합니다.-값을 딕셔너리에 저장합니다. p.s. python의 딕셔너리는 매핑(map)에 해당합니다.
3. 사용하여 필요없는 문자를 제거합니다
위 코드에서可以看到, str.strip(somechar)를 사용하여 str 앞뒤의 somechar 문자를 제거할 수 있습니다. somechar은 기호 또는 정규 표현식이 될 수 있습니다. 예를 들어: 위와 같이
item=item.strip()#문자열 앞뒤의 모든 음소를 제거합니다. 예를 들어: \t, \n 등 item=item.strip('\"')#앞뒤 제거 item=item.strip('\'') item=item.strip('+0*')#앞뒤 제거+00...00,*0의 개수는 무제한이며, 없을 수도 있습니다
4.re.match 문자열을 일치시킵니다
함수 문법:
re.match(pattern, string, flags=0)
함수 파라미터 설명:
파라미터 설명
pattern 일치할 정규 표현식
string 일치할 문자열.
flags 시그널 위치,정규 표현식의 일치 방식을 제어하는 데 사용됩니다. 예를 들어: 대소문자 구분 여부, 다중 줄 일치 등.
만약 일치가 성공하면 re.match 메서드는 일치 객체를 반환하며, 그렇지 않으면 None을 반환합니다。`
>>> s='2015-09-18'
>>> matchObj=re.match(r'\d{4}-\d{2}-\d{2}', s, flags= 0)
>>> print matchObj
<_sre.SRE_Match 객체 at 0x7f3525480f38>
1
2
3
4
5
5. time.strptime를 사용하여 문자열을 시간 객체로 변환합니다
time 모듈에서 time.strptime(str, format)는 str를 format 형식에 따라 시간 객체로 변환할 수 있습니다., format에서 일반적으로 사용되는 형식은 다음과 같습니다:
%y 2자리 연도 표현 (00-99)
%Y 4자리 연도 표현 (000-9999)
%m 월 (01-12)
%d 월의 일 (0-31)
%H 2412시간 시간수 (0-23)
%I 1212시간 시간수 (01-12)
%M 분 수 (00=59)
%S 초 (00-59)
In addition, you need to use the re module to match strings with regular expressions to see if they are in a general time format, such as YYYY/MM/DD H:M:S, YYYY-MM-DD 등
In the above code, the function catchTime checks whether item is a time object, and if so, converts it to a time object.
Code as follows:
import time import re def catchTime(item): # check if it's time matchObj=re.match(r'\d{4}-\d{2}-\d{2}',item, flags= 0) if matchObj!= None : item =time.strptime(item,'%Y-%m-%d') #print "returned time: %s " %item return item else : matchObj=re.match(r'\d{4}/\d{2}/\d{2\s\d+:\d+:\d+',item,flags=0 ) if matchObj!= None : item =time.strptime(item,'%Y/%m/%d %H:%M:%S') #print "returned time: %s " %item return item
Complete code:
import collections import time import re class UserInfo(object): 'Class to restore UserInformation' def __init__ (self): self.attrilist=collections.OrderedDict()# ordered self.__attributes=[] def updateAttributes(self,attributes): self.__attributes=attributes def updatePairs(self,values): for i in range(len(values)): self.attrilist[self.__attributes[i]]=values[i] def catchTime(item): # check if it's time matchObj=re.match(r'\d{4}-\d{2}-\d{2}',item, flags= 0) if matchObj!= None : item =time.strptime(item,'%Y-%m-%d') #print "returned time: %s " %item return item else : matchObj=re.match(r'\d{4}/\d{2}/\d{2\s\d+:\d+:\d+',item,flags=0 ) if matchObj!= None : item =time.strptime(item,'%Y/%m/%d %H:%M:%S') #print "returned time: %s " %item return item def ObjectGenerator(maxlinenum): filename='/홈/thinkit/문서/usr_info/USER.csv attributes=[] linenum=1 a=UserInfo() file=open(filename) while linenum < maxlinenum : values=[] line=str.decode(file.readline(),'gb2312)#linecache.getline(filename, linenum,'gb2312) if line=='': print'reading fail! Please check filename!' break str_list=line.split(',') for item in str_list : item=item.strip() item=item.strip('\"') item=item.strip('\'') item=item.strip('+0*) item=catchTime(item) if linenum==1: attributes.append(item) else : values.append(item) if linenum==1: a.updateAttributes(attributes) else : a.updatePairs(values) yield a.attrilist # 'a'를 사용하려면 ' '으로 변경 linenum = linenum +1 if __name__ == '__main__': for n in ObjectGenerator(10) : print n # 딕셔너리 출력, 정확한지 확인
결론
이 글의 모든 내용이 끝입니다. 여러분의 학습이나 업무에 도움이 되길 바랍니다. 의문이 있으면 댓글로 교류해 주세요. 감사합니다. 나아침 교육의 지원에 감사합니다.