반응형

**mongo db

1.mongo db설치

=>windows용은 msi버전(gui tool compasss를 같이 설치할 수 있는 옵션)을 다운로드 받아서 설치해도 되고 zip버전을 받아서 압축을 풀어도 됩니다.

 

2.mongo db서버 실행

=>mongo db 디렉토리에 가면 bin디렉토리에 있는 mongod라는 명령으로 서버를 실행

cmd > mongod --dbpath데이터베이스파일경로

C:\mongodata

mongod -dbpath C:\mongodata

 

=>처음 실행하는 경우에는 데이터베이스 파일이 저장될 디렉토리를 생성

 

=>명령어를 편리하게 사용할려면 bin디렉토리를 path환경변수에 추가해주면 됩니다.

 

3.mongo db클라에언트 실행(접속하는 것)

1)mongo db를 설치하면 mongo라는 command line기반의 접속 프로그램 제공

mongo db설치 디렉토리 안의 bin이라는 디렉토리에 존재

 

자신의 컴퓨터에서 실행 중인 데이터베이스 접속할 때는 아래 명령

cmd > mongo

 

원격에 있는 컴퓨터의 mongo db 접속

cmd > mongo –-host ip주소 :포트번호

cmd > mongo –-host ip주소 --port포트번호

ip주소 대신에 도메인도 가능

 

 

 

2)gui program을 설치해서 접속

=>가장 많이 사용하는 프로그램은 robomongo

https://studio3t.com/download-thank-you/?OS=win64

참조 사이트 : https://soye0n.tistory.com/149

 

 

4.데이터 저장 단위

database -> collection (table) ->document(- row)->field( -column)

1)데이터베이스 생성 및 사용

use 데이터베이스이름

=>없는 데이터베이스 이름을 사용하면 새로 생성되고 있는 데이터베이스 이름을 사용하면 접속

 

2)컬렉션 생성 및 사용

=>생성 명령 : db.createCollection(“컬렉션 이름”)

=>없는 컬렉션이더라도 db.컬렉션이름.insert()을 하게 되면 자동으로 생성

:

TABLE

이름

점수

 

 

 

 

 

 

5.데이터 저장

1. 데이터 표현

=>하나의 객체: {“속성이름”:데이터, ... }

=>여러 개의 데이터:[데이터 나열] – 값만 나열해도 되고 객체를 나열해도 됩니다.

 

2)데이터 삽입 함수

=>insert

db.컬렉션이름.insert(데이터)

데이터에 배열을 대입하면 배열을 분해해서 하나하나 삽입합니다.

mongo db는 최상위 루트에 배열을 허용하지 않습니다.

[]->이것으로 시작하는 것이 없고 {}것으로 된다.

 

=>데이터 확인 함수

db.컬렉션이름.find()

 

 

=>실습

데이터베이스 사용 명령: > use sample

데이터 삽입 명령 :   > db.users.insert({"name":"kim",score:90})              

> db.users.insert([{"name":"lee",score:80},{"name":"park","score":95}])

데이터 확인:      >db.users.find()

 

=>데이터를 확인해보면 직접 삽입하지 않은 _id라는 필드에 ObjectId라는 데이터가 삽입되어 있는데 이 필드는 직접 입력하지 않으면 mongo db document를 구분하기 위해서 자동으로 삽입하는 값입니다.

mongo db에서 id라는 필드를 만드는 것은 권장하지 않습니다.

 

=>insertOne insertMany함수를 이용해서 데이터를 삽입하는 것도 가능

insertOne은 하나의 데이터를 삽입할 때 사용하고 insertMany는 여러 개의 데이터를 삽입할 때 사용합니다.

 

3)데이터 삽입할 때 옵션

ordered 라는 옵션이 있는데 이 옵션은 데이터를 여러 개 삽압할 때 사용할 수 있는 옵션인데

ordered true로 설정되면 싱글 스레드를 이용해서 데이터를 삽입하는데 이 의미는 데이터를 순서대로 하나씩 삽입하는 것이고 ordered false로 설정하면 멀티 스테드를 이용해서 데이터를 삽입하는데 데이터를 동시에 삽입합니다.

 

차이점은 중간에 오류가 발생했을 때 ordered true이면 오류가 발생한 지점부터 데이터가 삽입되지 않습니다.

false로 설정되면 오류가 발생한 데이터만 삽입되지 않고 나머지 데이터는 삽입이 됩니다.

 

대량의 데이터를 약간의 오류를 무시하고 빠르게 삽입할려면 ordered옵션을 false로 설정합니다.

옵션이 없을 경우 ture

4)ordered옵션의 차이를 알아보기 위한 실습

users의 모든 데이터 삭제 >db.users.drop()

 

동일한 name을 삽입하면 오류를 발생시키기 위해서  name필드를 유일한 인덱스로 설정

users에 유니크 한 인덱스 설정 >db.users.createIndex({name:1},{unique:true})

db.users.insert({"name":"kim",score:90})

db.users.insert([{"name":"lee",score:80},{"name":"kim","score":95},{"name":"park","score":95}],{ordered:true})

db.users.find()

=>결과로 kim lee만 조회됩니다.

kim을 삽입할 때 오류가 발생해서 그 이후 데이터는 삽입되지 않습니다.

 

ordered  true일 경우 오류나면 뒤에는 안 들어간다.

ordered false일 경우 같이 들어가서 들어간다.

관계형 db는 제약조건 위반이면 무조건 안들어간다.

 

 

db.users.insert([{"name":"lee",score:80},{"name":"kim","score":95},{"name":"park","score":95}],{ordered:false})

db.users.find()

=>중간에 오류가 발생하더라도 park이 삽입됩니다.

동시에 삽입했기 때문에 데이터가 삽입될 때 다른 부분에 오류가 발생한 것은 상관하지 않습니다.

 

_id 수정,저장 조회 등 가능하는데 잘 하지 않는다.

 

=>기본적으로 single thread

mongo db

node.js

 

5).mongo db의 옵션에 대한 이행

잘못된 옵션을 사용해도 오류가 발생하지 않는 경우가 있습니다.

자바스크립트 함수는 필요한 옵션만 추출해서 사용하기 때문입니다.

 

6).ObjectId 직접 생성

=>_id 필드에 직접 값을 설정하는 것이 가능

=>ObjectId(“문자열 24자리”)로 생성할 수 있고 일련번호 처럼 new ObjectId()로 생성이 가능

=>inert함수를 이용해서 _id값을 직접 입력하면 동일한 값이 있을 때 에러를 발생시키고 save는 동일한 값이 있으면 수정을 합니다.

일련번호 형식으로 바꾼다. 일련번호 갑자기 바꾸는 것은 thread등 사용했기 때문이다.

var temp = new ObjectId()

print(temp)

 

패턴을 있으면

 

6.robomongo –mongo db에 접속해서 사용할 수 있는 gu tool

=>mongo db이 데이터를 sql형식으로도 조회 가능

 

use sample

db.users.find()

 

=>connect를 만들고  intellishell을 열면 명령어를 입력해서 결과 확인 가능

=>sql을 열면 sql 을 입력해서 mongo db의 데이터 사용가능

 

7.데이터 수정

1)수정메소드

update, updateOne, updateMany, replaceOne 추가

 

2)update함수

db.컬렉션이름.update({조건},{수정할 내용},{옵션})

=>옵션은 생략하면 기본값으로 설정

=>기본적으로 조건에 맞는 데이터 1개만 수정합니다.

 

3)수정 실습

샘플 데이터 1개 삽입

db.users.insert({"name":"강감찬",score:90})

 

수정 해주는 함수 호출

db.users.insert({"name":"강감찬"},{score:80})

 

별다른 옵션 없이 수정할 내용을 입력하면 수정할 내용으로 데이터가 대체됩니다.

위의 경우 name:강감찬 , score:90이라는 데이터가 score:80으로 대체됩니다.

 

db.users.find()

 

이름이 날라간다.

 

4)수정 내용에 설정하는 옵션

$set: 특정 필드만 수정할 때 사용

$unset:특정 필드를 제거

$inc : 특정 필드의 값에 더하기  => 조회수

$mul:특정 필드의 값에 곱하기

$rename :필드이름 변경

$currentDate: 현재 시간으로 설정  =>글을 수정한 날짜

 

데이터 1개 삽입

db.users.insert({"name":"굴리트","score":98,"nation":"holland"})

db.usres.find()

 

굴리트의 score 99로 수정

db.users.update({"name":"굴리트"},{$set:{"score":99}})

db.users.find()

 

 

굴리트의 nation 필드를 삭제

db.users.update({"name":"굴리트"},{$unset:{"nation":99}})

db.users.find()

굴리트의 score필드의 값을 5증가

db.users.update({"name":"굴리트"},{$inc:{"score":5}})

db.users.find()

 

굴리트의 lastModified필드의 값을 현재 시간으로 설정

db.users.update({"name":"굴리트"},{$currentDate:{"lastModified":true}})

db.users.find()

 

5)update 3번째 옵션

upsert:true로 설정하면 조건에 맞는 데이터가 없으면 insert

(update insert)

db.users.update({"name":"반바스텐"},{$set:{"score":89}})

db.users.find()

=>위의 경우는 조건에 맞는 데이터가 없어서 아무일도 발생하지 않습니다.

 

db.users.update({"name":"반바스텐"},{$set:{"score":89}},{upsert:true})

db.users.find()

조건에 맞는 데이터가 없으므로 반바스텐 89라는 데이터가 삽입

 

마지막 로그인 user의 시간을 업데이트 할때

한번도 로그인 하지 않는 분도 입력할 수 있다.

로그인 이력 : 로그인 id, 시간

a 12시에 로그인하면 수정하면 되는데

b가 없을 경우 13시에 업데이트 해야 하는데 없을 경우 추가한다.

 

multi:true로 설정하면 조건에 맞는 모든 데이터가 수정

(기본은 false여서 하나만 수정된다.)

 

 

RDBMS(관계형 데이터베이스)

테이블 설계

기본키 모든 데이터를 유일하게 구분

인덱스 설정

기본키로 하면 빨리 찾을 수 있다.

 

게시글

게시글 번호 (pk)

제목

내용

댓글은 내용(여러개 있을 수 있어서 게시글 테이블에 추가하면 안된다.)

 

댓글번호

게시글 번호

댓글 내용

 

 

 

 

 

 

 

 

 

 

join을 한다. 그래서 늦어 질 수 있다.

댓글 접고 원본글 내용에서 보다가 댓글클릭시 댓글만 조회된다.

 

 

No SQL

테이블 설계과정이 없다.

게시글번호

제목

내용

댓글 [{댓글번호: , 내용: }]

따로 따로 만들어서 join 을 할 필요없다.

$set

$push

$pull

 

stack

queue

push pop/pull(javascript)

 

카카오 spring hibernate

게시판

저장의 개념

변수  (프로그램 끝다 키면 없어진다.) 일시적이다.

파일 영구적으로 저장할 목적이다. 파일은 다른 데서 사용하려면 피씨가 켜져있어야 한다.

서버 외부에 파일로 저장 주기적으로 백업하고 켜놓는다.------------->저장 을 db(검색에 특화)

 

스마트폰은 컴퓨터이지만 서버로 될수 없다 돌아다니면서 IP가 변한다

내 카카오하고 친구 카카오 통신 하려면 중간에 고정 IP로 한다.

카카오 -> 카카오 서버 -> 애플서버 -> 친구 카카오에게 보낸다.(스마트폰 욺직이여서 )

서버 는 고정적인 이름(도메인)이나 주소(IP)가 있어야 한다.

 

6)필드에 배열이 있을 때 수정

배열에 데이터를 추가할 때$push

배열에서 데이터를 제거할 때는 $pul을 사용

 

//reply라는 필드에 배열을 소유하고 있는 데이터 생성

db.board.insert({"board_num":1,"board_id":"ggangpae1","board_title":"가입인사","board_content":"안녕하세요 반갑습니다.","reply":[]})

db.board.find()

 

board_num 1번인 데이터의 reply에 데이터를 추가

db.board.update({"board_num":1},{$push:{"reply":{"reply_num":1,"reply_content":"환영합니다.","reply_id":"admin","reply_time":ISODate("2019-1231T12:19:00")}}})

 

//2019-1231 날 짜만 할 겨우

//z는 더 아래 단위 천...

board_num 1번이고  reply_num 1번인 데이터의 content time을 수정

db.board.update({"board_num":1, "reply.reply_num":1},{$set:{"reply.$":{"reply_num":1"reply_content":"안녕.", "reply_time":ISODate("2019-1231T12:26:00")}}})

 

board_num 1번인 데이터의 reply_num 1번인 데이터를 삭제

db.board.update({"board_num":1},{$pull:{"reply":{"reply_num":1}}})

 

각각의 작업을 수행하고 match가 몇개 되는지 확인

조건에 맞는 데이터가 없으면 match된 데이터가 없다고 나옵니다.

옵션들에 따옴표를 해도되고 하지 않아도 됩니다.

 

8.데이터 삭제

remove()

deleteOne()

deleteMany()

 

=>remove의 첫번째 매개변수는 삭제할 조건입니다.

두번째 매개변수는 justOne이라는 옵션인데 true로 설정하면 1개만 지워지고 생략하거나 false로 설정하면 조건에 맞는 데이터가 모두 삭제됩니다.

 

9.컬렉션 삭제는 drop입니다.

board_num 1인 데이터 모두 삭제

 

db.board.remove({"board_num":1})

db.board.find()

 

board라는 컬렉션을 삭제

db.board.drop()

db.borad.find()

 

10.MOngo DB에서 documnet를 삽입 ,삭제,갱신 하는 것도 중요하지만 mongo db는 자식 테이블을 별도로 만들지 않고 부모 테이블에 배열의 형태로 저장하기 때문에 배열의 데이터를 삽입,삭제 ,갱신하는 것도 중요합니다.

 

11.bulkWrite

=>삽입 ,삭제 , 갱신을 동시에 수행할 수 있는 함수

=>insertOne,updateOne,updateMany, deleteOne,deleteMany함수를 사용

 

삽입과 수정을 하나의 명령어로 수행하도록 bulkWrite 사용

//90으로 여고 88로 변경된다.

db.board.bulkWrite([{insertOne:{"document":{"name":"kim","score":90}}},{updateOne:{"filter":{"name":"kim"},"update":{$set:{"score":88}}}}])

 

db.board.find()

 

 

12.데이터 검색

=>find()함수 이용

=>첫번째 매개변수로 조건을 설정하고 두번째 매개변수로 조회할 필드를 설정

=>매개변수를 아무것도 대입하지 않으면 컬렉션의 모든 데이터 조회

 

1).users컬렉션의 모든 데이터 조회

db.users.find()

 

2)특정 필드만 출력하거나 제외

=>두번째 매개변수에 {필드이름:0 또는 1,...}

=>0이 설정되면 출력하지 않고 1이 설정되면 조회

 

users에서 _id name만 조회

>db.users.find({},{"name":1})

usres에서 name만 제외

>db.users.find({},{"name":0})

db.users.find({},{"name":1,"score":1})

db.users.find({},{"name":0,"score":0})

조회시 1 1 끼리 0 0끼리 사용해야 한다. 혼용하면 오류 난다.

 

3.조건 설정

{필드이름:,...}

=>필드의 값이 값고 일치하는 데이터만 조회

=>여러 개의 조건을 나열하면 and입니다.

 

4)조건 연산자

$eq    : = 와 같은 기능으로 이 기능을 사용하지 않고 값을 직접 설정하는 형태를 사용

$ne    : <> != 같은 기능

$lt(lte): <(<=)

gt(gte): > (>=)

 

$in:배열에 속하는 경우

$nin:배열에 속하지 않는 경우

 

$not:반대로

$or: 또는

$and:그리고

$nor:not or

4개는 사용방법이 같다.

db.users.find( {$or: [ {name:"반바스텐"}, {password:89} ] })

 

users에서 score 90이 넘는 데이터만 조회

db.users.find({'score' :{$gt:90}})

 

users 에서 name이 굴리트 이거나 반바스텐인 데이터 조회

db.users.find({'name':{$in :['굴리트','반바스텐']}})

db.users.find({'name':{$nin :['굴리트','반바스텐']}})

 

5)like

=>정규식(Regular Expression - RegExp) 패턴을 사용

문자열에서 특정 패턴을 문자열을 조회하기 위해서 사용하는 문법

[0-9]

[-]

이메일은 정해진 단어가 아니다.

pattern을 뺄 경우 정규식 사용한다.

[A-Za-z]

 

users에서 name이 굴로 시작하는 데이터만 조회

db.users.find({'name':/.*/})

db.users.find({'name':/^/})

 

users에서 텐으로 끝나는 데이터만 조회

db.users.find({'name':/$/})

 

정규식:문자열에서 원하는 글자를 찾는 것이다.

여기 원래 정규식이였다.

 

6)findOne

=>1개만 조회

 

7)find().limit(개수)

 

8)find().skip(개수)

 

9)find().sort({필드이름:1 또는 -1,...})

=>1을 오름차순 정렬이고 -1을 설정하면 내림차순

 

10)limit,skip,sort는 조합할 수 있습니다.

db.users.find().skip(0).limit(1) // 여기 숫자는 chunk

db.users.find().skip(1).limit(1) // 몇개를 띄여쓰고 몇개를 찾을 가?

db.users.find().sort({"name":1}) //이름의 오름차순 정렬

chunk 는 분할 한다는 의미이다.

python에서는 chunk사용한다.

db.users.find().sort({"name":-1})

크기 비교할때 보통 3개 로 돌아온다.

 

11)cursor

=>여러 개의 데이터가 있을 때 하나씩 접근 할 수 있도록 해주는 포인터

=>다음 데이터 존재여부를 알려주는 메소드와 다음 데이터로 이동하는 메소드를 가지고 있습니다.

cursor는 첫번째 데이터를 가르키지 않는다.

그래서 첫번때 데이터를 읽으려면 next를 해야한다.

begin of file =>출발점 bof

데이터가 없는 끝나는 자리는 end of file(EOF)

자료구조에선느 BOF->HEAD

                  EOF->TAIL

다음 있냐 없냐는가 아니면 다음으로 넘어가는 것 등은 next이다.

 

데이터를 하나씩 접근

var cur = db.users.find()

 

데이터 존재 여부를 확인

cur.hasNext()

true false가 리턴

true가 리턴되면 다음 데이터가 잇는 것이고 false가 리턴되면 다음 데이터가 없는 경우

 

다음 데이터가 존재하는 경우 다음 데이터 확인

cur.next()

 

var cur = db.users.find()

cur.hasNext()

cur.next()

#프로그래밍에서 가져온다.

 

**Map – Reduce(맵 리듀스)

=>데이터의 모임에 집계를 적용한 후 연산을 수행해도록 하는 것

=>연산이나 집계 적용단위는 함수

 

1.샘플 데이터 생성 -CLASS별로 score의 합계를 구할려고 합니다.

db.map.insert({"name":"kim",score:76,"class":"A"})

db.map.insert({"name":"lee",score:85,"class":"B"})

db.map.insert({"name":"park",score:91,"class":"A"})

db.map.insert({"name":"choi",score:65,"class":"B"})

 

2.Map –Reduce Programming에서는 2개의 함수가 필요

집계를 위한 함수 그룹화할 함수

연산을 수행할 함수 연산 함수

 

#집계

var mapper = function(){

           emit(this.class, {score:this.score});

}

 

#연산

 

var reducer = function(key,values){

           var sum = 0;

           values.forEach(function(doc){

                       sum = sum + doc.score;

    });

    return {score:sum};

}

sum = sum + 1;=>개수가 된다.

#map-reduce 수행

db.map.mapReduce(mapper,reducer,{out:{inline:1}})

 

Hadoop            분산저장처리 기술

분산시스템은 각자 연산해서 한다.

**python mongo db연동

=>pymongo라는 패키지를 이용

1.pymongo패키지를 설치

cmd창에서 >pip install pymongo

python은 프로그램 수행도중에 설치 해도 괜찮다.

R은 다시 설치하면 restart된다.

 

2.mongo db연결

변수 = pymongo.MongoClient("ip주소","포트번호")

=>포트번호를 생략하면 27017

=>ip주소를 생략하면 로컬 컴퓨터

 

3.데이터베이스 설정

데이터베이스 변수 = 변수.데이터베이스이름

=>데이터베이스 이름이 없으면 새로 만들어 집니다.

 

4.컬렉션 설정

컬렉션변수 = 데이터베이스변수.컬렉션이름

=>컬렉션 이름이 없으면 새로 만들어 집니다.

 

5.실습

데이베이스 연결 및 컬렉션 연결

 

from pymongo import MongoClient

 

'''

데이터베이스 연결

'''

con = MongoClient()

#print(con)

 

'''

con 이 사용할 수 있는 속성과 메소드 확인

'''

#print(dir(con))

 

'''

데이터베이스 연결 및 생성

'''

db = con.mymongo

 

'''

컬렉션 연결 및 생성

'''

collection = db.sample

 

6.데이터 삽입

컬렉션.insert_one(dict 객체)

컬렉션.insert_many(list객체)

=>insert메소드가 있는데 deprecated

 

7.데이터 삽입 실습

dict1 = {"name":"kim","nation":"라이베리아"}

dict2 = {"name":"
요한","nation":"네덜란드"}
dict3 = {"name":"
에우","nation":"포르투칼"}
li = [dict2, dict3]

'''
데이터 삽입
'''
collection.insert_one(dict1)
collection.insert_many(li)

 

collection.insert(dict1)

C:/OracleConnect/mongoConnect.py:28: DeprecationWarning: insert is deprecated. Use insert_one or insert_many instead.

  collection.insert(dict1)

deprecated사용해도 되지만 없어질 수 있다.

 

8.데이터 조회

find_one(하나) find(여러개)함수를 이용

mongo db는 하나의 행을 dict로 만들어 줍니다.

 

분석 할려고 하면  자료형 무조건 확인 하는게 좋다.

'''
데이터 조회
'''
result = collection.find_one()
#print(type(result))
#<class 'dict'>
#dict
는 바로 출력해도 되고 dict['key']를 이용해서 부분적으로 사용
print(result)
print(result["name"])

result = collection.find()
#print(type(result))
#<class 'pymongo.cursor.Cursor'>
#
자료형이 class -> cursor
#
자료형이 모르는 클래스라서 사용 가능한 속성을 확인
#print(dir(result))
#iterator
여러개 데이터 순서대로 조회
#__iter__ 가 있으면 for - in 사용가능
#for i in []:
for i in result:
    print(i)

result = collection.find({"name":"
요한"})
for temp in result:
    print(temp)

 

result = collection.find({"name":"조지웨아"})

#print(type(result))

#자료형이 모르는 클래스라서 사용 가능한 속성을 확인

#__iter__ 가 있으면 for - in 사용 가능

#print(dir(result))

for temp in result:

    print(temp)

 

9.수정

update_one update_many

'''
데이터 수정
'''
#name
kim인 데이터의 nation을 모장비크로 변경
collection.update_one({"name":"kim"},{"$set":{"nation":"모장비크"}})
#update_many
다 바꿔진다.
result = collection.find()
for temp in result:
    print(temp)

 

 

 

10.삭제

delete_one() delete_many()

삭제하는 것은 경고하고 없에는 것이다.

'''
데이터 삭제
'''
collection.delete_one({"name":"kim"})
#update_many
다 바꿔진다.
result = collection.find()
for temp in result:
    print(temp)

 

 

java

gui프로그램

andriod

java network db연결

 

반응형

'Study > DB' 카테고리의 다른 글

DB-5  (0) 2020.09.17
DB-4  (0) 2020.09.15
DB-3  (0) 2020.09.15
DB-2  (0) 2020.09.13
DB-1  (0) 2020.09.13
반응형

7. 정규 표현식

 

I. 정규 표현식 살펴보기

정규 표현식(Regular Expressions) 은 복잡한 문자열을 처리할 때 사용하는 기법으로 문자열을 처리하는 모든 곳에서 사용함

isdigit()는 음수나 소숫점이 포함된 숫자는 False를 리턴한다. 대충 생각해서는 왠지 될 것 같은데 안된다.

정규 표현식은 왜 필요한가?

주민등록번호를 포함하고 있는 텍스트가 있다. 이 텍스트에 포함된 모든 주민등 록번호의 뒷자리를 * 문자로 변경해 보자.

정규식을 모르면, 다음과 같은 순서로 프로그램을 작성해야 할 것임

1. 전체 텍스트를 공백 문자로 나눈다(split).

2. 나뉜 단어가 주민등록번호 형식인지 조사한다.

3. 단어가 주민등록번호 형식이라면 뒷자리를 *로 변환한다.

4. 나뉜 단어를 다시 조립한다.

주민등록번호의 뒷자리를 * 문자로 구현한 코드

data = """

park 800905-1049118

kim  700905-1059119

"""

 

result = []

for line in data.split("\n"):

    word_result = []

    for word in line.split(" "):

        if len(word) == 14 and word[:6].isdigit() and word[7:].isdigit():

            word = word[:6] +"-" + "******"

        word_result.append(word)

    result.append(" ".join(word_result))

print("\n".join(result))   

 

data = """

park 800905-1049118

kim  700905-1059119

"""

 

result = []

for line in data.split("\n"):

    word_result = []

    for word in line.split(" "):#공백 문자마다 나누기

        if len(word) == 14 and word[:6].isdigit() and word[7:].isdigit():

            word = word[:6]+"-"+"*******"

        word_result.append(word)

    result.append(" ".join(word_result))#나눈 단어 조립하기

print("\n".join(result))                          

 

 

주민등록번호의 뒷자리를 * 문자로 구현한 정규 표현식

 

import re

pat = re.compile("(\d{6})[-]\d{7}")#class가 만든 객체

#(\d{6})[-]\d{7}자열을 확인

#()->group으로 하기->g1

#\d 숫자인 것을 찾아내라

print(pat.sub("\g<1>-*******",data))#함수 호출

 

###########정규표현식

import re

pat = re.compile("(\d{6})[-]\d{7}")#class가 만든 객체

#(\d{6})[-]\d{7}자열을 확인

#()->group으로 하기->g1

#\d 숫자인 것을 찾아내라

print(pat.sub("\g<1>-*******",data))#함수 호출

 

정규 표현식을 사용하면 훨씬 간편하고 직관적인 코드를 작성할 수 있음

찾으려는 문자열 또는 바꾸어야 할 문자열의 규칙이 매우 복잡하다면, 정규식의 효용은 더 커지게 됨

 

II. 정규 표현식 시작하기

=>정규 표현식의 기초, 메타 문자

 

메타 문자란 원래 그 문자가 가진 뜻이 아닌 특별한 용도로 사용하는 문자를 말함

 

==>문자 클래스 [ ]

'[ ] 사이의 문자들과 매치라는 의미를 갖음

하이픈(-)는 두 문자 사이의 범위(From - To)를 의미함

^는 반대(not)를 의미함

[a-zA-Z] :알파벳 모두

[0-9] : 숫자

자주 사용하는 문자 클래스

대문자로 사용된 것은 소문자의 반대임

 

==>Dot(.)

Dot(.) 메타 문자는 줄바꿈 문자인 \n을 제외한 모든 문자와 매치됨을 의미함

a.b “a + 모든 문자 + b” a하고 b사이 한문자

ab사이에 줄 바꿈 문자를 제외한 어떤 문자가 들어가도 모두 매치

a[.]b는 문자 . 그대로를 의미함 (“a + Dot(.)문자 + b”)

이 경우에는 "a.b" 문자열과 매치되고 "a0b" 문자열과는 매치되지 않는다.

 

==>반복(*) 

* 메타 문자는 반복을 의미함. 0부터 무한대로 반복될 수 있음

ca*t * 문자 바로 앞에 있는 a 0번 이상 반복되면 매치

ca*t  a 0번부터 무한 반복

 

==>반복(+) 

+ 메타 문자도 반복을 의미함. 최소 1번 이상 반복될 때 사용함

ca+t “c + a(1번 이상 반복) + t”

 

==>반복({m,n}, ?) 

반복 횟수를 제한하고 싶을 때 사용

{m,n}는 반복 횟수가 m부터 n까지 매치할 수 있음. m 또는 n을 생략할 수도 있음

{m,}는 반복 횟수가 m 이상이고, {,n}는 반복 횟수가 n 이하를 의미함

{1,} +와 동일하고, {0,} *와 동일함

 

1. {m}

ca{2}t a 2번 반복되면 매치, “c + a(반드시 2번 반복) + t”

 

2. {m,n}

ca{2,5}t a 2~5번 반복되면 매치,  “c + a(2~5번 반복) + t”

 

3.?

? 메타 문자는 {0, 1}을 의미함

ab?c b 0~1번 사용되면 매치,  “a + b(있어도 되고 없어도 된다) + c"

*, +, ? 메타 문자는 모두 {m, n} 형태로 고쳐 쓰는 것이 가능하지만, 가급적 간결한 *, +, ? 메타 문자를 사용하는 것이 좋음

 

파이썬에서 정규 표현식을 지원하는 re 모듈

re 모듈은 파이썬 설치할 때 자동으로 설치되는 기본 라이브러리임

>>> import re

>>> p = re.compile('ab*')

re.compile을 사용하여 정규 표현식을 컴파일함

re.compile의 결과로 돌려주는 객체 p (컴파일된 패턴 객체) 를 사용하여 그 이후의 작업을 수행함

 

==>정규식을 사용한 문자열 검색

컴파일된 패턴 객체는 4가지 메소드를 제공함

match() 문자열의 처음부터 정규식과 매치되는지 조사함

처음부분

search() 문자열 전체를 검색하여 정규식과 매치되는지 조사함

어디 있는 지 관계없다.

findall() 정규식과 매치되는 모든 문자열(substring)을 리스트로 돌려줌

객체로 돌려주면 class

findall은 함수이다.

finditer() 정규식과 매치되는 모든 문자열(substring)을 반복 가능한 객체로 돌려줌

match, search는 정규식과 매치될 때는 match 객체를 돌려주고, 매치되지 않을 때는 None을 돌려줌

 

#########match

>>> import re

>>> p = re.compile('[a-z]+')

>>> m = p.match("python")

>>> print(m)

>>> m = p.match("3 python")

>>> print(m)

match의 결과로 객체 또는 None 을 돌려주기 때문에 다음의 흐름으로 작성함

 

 

 

 

 

###########[]

#+최소한 한번 와야 한다 match

data=('python','3 python')

p = re.compile('[a-z]+')

for i in data:

    m = p.match(i)

    #print(m)

    #<re.Match object; span=(0, 6), match='python'>

    #None

    if m:

        print("Match Found match: ",m.group())

        print("Match Found match: ",m.start())

        print("Match Found match: ",m.end())

        print("Match Found match: ",m.span())

    else:

        print("No match match")

 

#########search

문자열 전체를 검색하여 정규식과 매치되는지 조사함

>>> import re

>>> p = re.compile('[a-z]+')

>>> m = p.search("python")

>>> print(m)

>>> m = p.search("3 python")

>>> print(m)

문자열 전체를 검색하기 때문에 “3” 이후의 “python” 문자열과 매치됨

 

for i in data:

    m = p.search(i)

    #print(m)

    #<re.Match object; span=(0, 6), match='python'>

    #<re.Match object; span=(2, 8), match='python'>

   

    if m:

        print("Match Found search: ",m.group())

    else:

        print("No match search")

 

#########findall

정규식과 매치되는 모든 문자열(substring)을 리스트로 돌려줌

>>> import re

>>> p = re.compile('[a-z]+')

>>> result = p.findall("life is too short")

>>> print(result)

result = p.findall("life1 is tooA short")

print(result)

#print(result[0])

 

#########finditer

정규식과 매치되는 모든 문자열(substring)을 반복 가능한 객체로 돌려줌

>>> result = p.finditer("life is too short")

>>> print(result)

>>> for r in result:print(r)

result = p.finditer("life is too short")

#print(result)#<callable_iterator object at 0x000002CE171C4CA0>

for i in result:

    print(i.group())

 

===> match, search 객체의 메소드

어떤 문자열이 매치되었는가?

매치된 문자열의 인덱스는 어디부터 어디까지인가?

 

match, search 객체의 메소드 사용 예:

>>> import re

>>> p = re.compile('[a-z]+')

>>> m = p.match("python")

>>> m.start()

>>> m.end()

>>> m.span()

>>> m = p.search("3 python")

>>> m.start()

>>> m.end()

>>> m.span()

         

메소드 결과값이 다르게 나오는 것을 확인할 수 있음

 

==>[모듈 단위로 수행하기]

re 모듈은 축약된 형태로 사용할 수 있는 방법을 제공함

이 방식은 잘 사용하지 않는다. 메소드를 다양하게 사용해야 하는데

이것은 한번밖에 사용 안 된다.

#m = re.match(patten,string)

 

 

 

한 번 만든 패턴 객체를 여러 번 사용해야 할 때는 re.compile을 사용하는 것이 좋음

 

=>컴파일 옵션

DOTALL            S         dot 문자(.)가 줄바꿈 문자를 포함하여 모든 문자와 매치함

IGNORECASE     I          · 소문자에 관계 없이 매치함

MULTILINE         M        여러 줄과 매치함 (^, $ 메타 문자의 사용과 관계가 있는 옵션임

각 라인의 처음 ^           각 라인의 마지막 $

VERBOSE          X         verbose 모드를 사용함 (정규식을 보기 편하게 만들 수도 있고, 주석 등을 사용할 수도 있음)

verbose  주석을 다라 주는 것

 

==> DOTALL, S

dot 문자(.)가 줄바꿈 문자(\n)를 포함하여 모든 문자와 매치함

re.DATALL 또는 re.S 옵션을 사용해 정규식을 컴파일하면 됨

>>> import re

>>> p = re.compile('a.b')

>>> m = p.match('a\nb')

>>> print(m)     # 문자열과 정규식이 매치되지 않음

 

>>> p = re.compile('a.b',re.DOTALL)

>>> m = p.match('a\nb')

>>> print(m)

 

>>> p = re.compile('a.b',re.S)

>>> m = p.match('a\nb')

>>> print(m)

 

==> IGNORECASE, I

re.IGNORECASE 또는 re.I 옵션은 대 · 소문자에 관계 없이 매치함

>>> p = re.compile('[a-z]',re.I)

>>> p.match('python')

<re.Match object; span=(0, 1), match='p'>

>>> p.match('Python')

<re.Match object; span=(0, 1), match='P'>

>>> p.match('PYTHON')

<re.Match object; span=(0, 1), match='P'>

 

==> MULTILINE, M

re.MULTILINE 또는 re.M 옵션은 메타 문자인 ^, $와 연관된 옵션임

^는 문자열의 처음을 의미하고, $은 문자열의 마지막을 의미함

>>> import re

>>> p = re.compile("^python\s\w+")

>>> data = """python one

life is too short

python two

you need python

python three"""

>>> print(p.findall(data))

['python one']

 

re.MULTILINE 또는 re.M 옵션은 ^, $ 를 문자열의 각 줄마다 적용해 주는 것임

>>> import re

>>> p = re.compile("^python\s\w+",re.MULTILINE)

>>> data = """python one

life is too short

python two

you need python

python three"""

>>> print(p.findall(data))

['python one', 'python two', 'python three']

 

 

==> VERBOSE, X

re.VERBOSE 또는 re.X 옵션은 정규식을 보기 편하게 주석 또는 줄 단위로 구분 할 수도 있음

 

 

 

 

 

 

 

 

문자열에 사용된 whitespace는 컴파일할 때 제거됨([ ]안은 제외)

줄 단위로 #기호를 사용하여 주석문을 작성할 수 있음

 

=> 백슬래시 문제

\section”와 같이 \ 문자가 포함된 문자열을 찾을 때 혼란을 줌

\section

\s 문자가 whitespace로 해석되어 의도한 대로 매치가 이루어지지 않음

[ \t\n\r\f\v]ection 도 동일하게 whitespace로 해석됨

정규식에서 사용한 \ 문자가 문자열 자체임을 알려 주기 위해 백슬래시 2개를 사용하여 이스케이프 처리를 해야 함

>>> p = re.compile('\\section')

>>> p = re.compile('\\\\section')

\를 사용한 표현이 너무 복잡하여 Raw String 규칙이 생겨나게 됨

>>> p = re.compile(r'\\section')

정규식 문자열 앞에 r 문자를 삽입하면, Raw String 규칙에 의하여 백슬래시 2개 대신 1개만 써도 2개를 쓴 것과 동일한 의미를 갖게 됨

 

import re

p = re.compile('\\section')

print(p.match('\section'))

#None

 

p = re.compile('\\\\section')

print(p.match('\section'))

#<re.Match object; span=(0, 8), match='\\section'>

 

#\를 사용한 표현이 너무 복잡하여 Raw String 규칙이 생겨나게 됨

p = re.compile(r'\\section')

print(p.match('\section'))

#<re.Match object; span=(0, 8), match='\\section'>

 

III. 강력한 정규 표현식의 세계로

그룹(Group)을 만드는 법, 전방 탐색 등 강력한 정규 표현식을 살펴봄

=>메타 문자

+, *, [], {} 등의 메타 문자는 매치가 진행될 때 매치되고 있는 문자열의 위치가 변경되지만 (소비된다고 표현) , 문자열을 소비시키지 않는 메타 문자도 있음

 

==>|

| 메타 문자는 or과 동일한 의미로 사용됨

>>> p = re.compile('Crow|Servo')

>>> m = p.match('CrowHello')

>>> print(m)

<re.Match object; span=(0, 4), match='Crow'>

 

==>^

^ 메타 문자는 문자열의 맨 처음과 일치함을 의미함

>>> print(re.search('^Life','Life is too short'))

<re.Match object; span=(0, 4), match='Life'>

>>> print(re.search('^Life','MyLife'))

None

 

p = re.compile('^Life')

print(p.search('Life is too short'))

#<re.Match object; span=(0, 4), match='Life'>

re 모듈의 축약된 형태

re.MULTILINE을 사용할 경우에는 여러 줄의 문자열일 때 각 줄의 처음과 일치함

 

==>$

$ 메타 문자는 문자열의 끝과 매치함을 의미함

>>> print(re.search('short$','Life is too short'))

<re.Match object; span=(12, 17), match='short'>

>>> print(re.search('short$','Life is too short,you need python'))

None

 

p = re.compile('short$')

print(p.search('Life is too short'))

#<re.Match object; span=(12, 17), match='short'>

 

==>\A 

\A는 문자열의 처음과 매치됨을 의미함

\A는 줄과 상관없이 전체 문자열의 처음하고만 매치됨

==>\Z 

\Z는 문자열의 끝과 매치됨을 의미함

\Z는 줄과 상관없이 전체 문자열의 끝과 매치됨

 

==>\b 

\b는 단어 구분자(Word boundary)이며, 단어는 whitespace에 의해 구분됨

>>> p = re.compile(r'\bclass\b')

>>>

>>> print(p.search('no class at all'))

<re.Match object; span=(3, 8), match='class'>

>>> print(p.search('the declassified algorithm'))

None

>>> print(p.search('one subclass is'))

None

\b는 파이썬 리터럴 규칙에 의하면 백스페이스(BackSpace)를 의미하므로, 구분자임을 알려 주기 위해 r’\bclass\b’처럼 Raw string임을 알려주는 기호r을 반드시 붙여 주어야 함

 

==>\B

\b의 반대로, \B whitespace로 구분된 단어가 아닌 경우에만 매치됨

>>> p = re.compile(r'\Bclass\B')

>>>

>>> print(p.search('no class at all'))

None

>>> print(p.search('the declassified algorithm'))

<re.Match object; span=(6, 11), match='class'>

>>> print(p.search('one subclass is'))

None

class 단어의 앞뒤에 whitespace가 하나라도 있는 경우에는 매치가 안됨

 

==>그루핑

ABC 문자열이 계속해서 반복되는지 조사하는 정규식을 작성하고 싶을 때 사용됨

: (ABC)+

>>> p = re.compile('(ABC)+')

>>> m = p.search('ABCABCABC OK?')

>>> print(m)

<re.Match object; span=(0, 9), match='ABCABCABC'>

>>> print(m.group())

ABCABCABC

 

\w+\s+\d+[-]\d+[-]\d+’이름 + “ “ + 전화번호형태의 문자열을 찾는 정규식

\w+\s+\d+[-]\d+[-]\d+

\w 문자 숫자

\s white space

>>> p = re.compile(r"\w+\s+\d+[-]\d+[-]\d+")

>>> m = p.search("park 010-1234-1234")

그룹핑하고이름부분만 뽑아내기

>>> p = re.compile(r"(\w+)\s+\d+[-]\d+[-]\d+")

>>> m = p.search("park 010-1234-1234")

>>> print(m.group(1))

park

이름에 해당하는 ‘\w+’ 부분을 그룹 ‘(\w+)’으로 만들면, match 객체의 group(인덱스) 메소드를 사용하여 그루핑된 부분의 문자열만 뽑아낼 수 있음

 

==>‘전화번호’ 부분만 뽑아내기

>>> p = re.compile(r"(\w+)\s+(\d+[-]\d+[-]\d+)")

>>> m = p.search("park 010-1234-1234")

>>> print(m.group(2))

010-1234-1234

 

==>‘국번’ 부분만 뽑아내기

>>> p = re.compile(r"(\w+)\s+((\d+)[-]\d+[-]\d+)")

>>> m = p.search("park 010-1234-1234")

>>> print(m.group(3))

010

그룹이 중첩되어 있는 경우는 바깥쪽부터 시작하여 안쪽으로 들어갈수록 인덱스가 증가함

 

 

==>그루핑된 문자열 재참조하기

>>> p = re.compile(r'(\b\w+)\s+\1')

>>> p.search('Paris in the the spring').group()

'the the'

정규식 ‘(\b\w+)\s+\1’ ‘(그룹) + “ “ + 그룹과 동일한 단어와 매치됨을 의미

2개의 동일한 단어를 연속적으로 사용해야만 매치됨

\1은 정규식의 그룹 중 첫 번째 그룹을 가리키고, \2는 두 번째 그룹을 참조함

\1 한번더 쓰라  첫번때 그룹 재창조 하고 싶을때 \1

두번째 그룹 \2

 

=>그루핑된 문자열에 이름 붙이기

정규식 안에 그룹이 많고 그룹이 추가 및 삭제되면, 그 그룹을 인덱스로 참조한 프로그램도 모두 변경해 주어야 하는 위험이 있음

이러한 이유로 그룹 이름을 지정할 수 있게 했음

(?P<name>\w+)\s+((\d+)[-]\d+[-]\d+)

그룹에 이름을 지어 주려면, (\w+)  (?P<name>\w+) 변경하면 됨

>>> p = re.compile(r'(?P<name>\b\w+)\s+((\d+)[-]\d+[-]\d+)')

>>> m = p.search("park 010-1234-1234")

>>> print(m.group("name"))

park

print(m.group("name"))print(m.group(1)) 결과는 같다.

name이라는 그룹 이름으로 참조할 수 있음

>>> p = re.compile(r'(?P<word>\b\w+)\s+(?P=word)')

>>> p.search('Paris in the the spring').group()

'the the'

그룹 이름도 정규식 안에서 재참조할 때는 (?P=그룹이름) 확장 구분을 사용함

 

=>전방 탐색

[.] ->새파일.txt .표현

#긍정형 전방 탐색

>>> p = re.compile(".+:")

>>> m = p.search("http://google.com")

>>> print(m.group())

http:

?=: : 으로 제외하는데 :이것으로 끝내는 것 찾기

.+:”과 일치하는 문자열로 http:를 돌려줌

http:라는 검색 결과에서 :을 제외하고 싶을 때, 전방 탐색임

==>긍정형 전방 탐색

>>> p = re.compile(".+(?=:)")

>>> m = p.search("http://google.com")

>>> print(m.group())

http

http:라는 검색 결과에서 :을 제외하고 돌려줌

 

==>부정형 전방 탐색

확장자가 bat가 아닌 경우에만 통과된다는 의미임

확장자가 bat 또는 exe가 아닌 경우에는 통과된다는 의미임

p = re.compile(".*[.](?!bat$).*$")

#.* -> * 0번부터

#bat 가 아닌 것을

m = p.search("aa.exe")

print(m)

 

p = re.compile(".*[.](?!bat$|exe$).*$")

#.* -> * 0번부터

#bat 가 아닌 것을

#[.] 실제 점을 찍고 싶을 때

m = p.search("aa.txt")

print(m)

 

=>문자열 바꾸기

sub 메소드를 사용하면 정규식과 매치되는 부분을 다른 문자로 쉽게 바꿀 수 있음

>>> p = re.compile('(blue|white|red)')

>>> p.sub('colour','blue socks and red shoes')

'colour socks and colour shoes'

위에 색상을 colore를 바꾸기

sub 메소드의 첫 번째 매개변수는바꿀 문자열이 되고, 두 번째 매개변수는 ‘대상 문자열이 됨

바꾸기 횟수를 제어하려면, 세 번째 매개변수로 count 값을 넘기면 됨

===>한번 만 바꾸기

>>> p.sub('colour','blue socks and red shoes',count=1)

'colour socks and red shoes'

===>count를 해서 바꾸기

print(p.sub('colour','blue socks and red shoes',count = 2))

colour socks and colour shoes

print(p.sub('colour','blue socks and red shoes',count = 3))

colour socks and colour shoes

 

==>sub 메소드와 유사한 subn 메소드

>>> p = re.compile('(blue|white|red)')

>>> p.subn('colour','blue socks and red shoes')

('colour socks and colour shoes', 2)

 

==>sub 메소드를 사용할 때 참조 구문 사용하기

>>> p = re.compile(r"(?P<name>\w+)\s+(?P<phone>(\d+)[-]\d+[-]\d+)")

>>> print(p.sub("\g<phone> \g<name>","park 010-1234-1234"))

010-1234-1234 park

‘\g<그룹 이름>’을 사용하면 정규식의 그룹 이름을 참조할 수 있게 됨

>>> p = re.compile(r"(?P<name>\w+)\s+(?P<phone>(\d+)[-]\d+[-]\d+)")

>>> print(p.sub("\g<2> \g<1>","park 010-1234-1234"))

010-1234-1234 park

 

==>sub 메소드의 매개변수로 함수 넣기

>>> def hexrepl(match):

    value = int(match.group())

    return hex(value)

 

>>> p = re.compile(r'\d+')

>>> p.sub(hexrepl,'Call 65490 for printing, 49152 for user code.')

'Call 0xffd2 for printing, 0xc000 for user code.'

 

=>Greedy vs Non-Greedy

#print(re.match('<.*>', s).span())

#<. 문한 >

#*->? ?표를 0아니면 1번 나오게 하라

>>> s = '<html><head><title>Title</title>'

>>> len(s)

32

>>> print(re.match('<.*>',s).span())

(0, 32)

>>> print(re.match('<.*>',s).group())

<html><head><title>Title</title>

‘<.*>’ 정규식의 매치 결과로 * 메타 문자는 탐욕스러워서(Greedy) 최대한의 문자열을 모두 소비해 버림

 

>>> print(re.match('<.*?>',s).group())

<html>

non-greedy 문자인 ? *?, +?, ??, {m,n}?와 같이 사용할 수 있음

 

 

 

연습문제

1.

>>> a = "a:b:c:d"

>>> b = a.split(":")

>>> print("#".join(b))

a#b#c#d

 

2.

>>> a = {'A':90,'B':80}

>>> a['C']

Traceback (most recent call last):

  File "<pyshell#77>", line 1, in <module>

    a['C']

KeyError: 'C'

===========================>

>>> a = {'A':90,'B':80}

>>> a.get('C',70)

70

 

3.

>>> a = [1,2,3]

>>> a = a + [4,5]

>>> a

[1, 2, 3, 4, 5]

>>> a = [1,2,3]

>>> a.extend([4,5])

>>> a

[1, 2, 3, 4, 5]

id로 구분한다.

>>> a = [1,2,3]

>>> id(a)

1353827821696

>>> a = a + [4,5]

>>> id(a)

1353827491904

>>> a = [1,2,3]

>>> id(a)

1353827822336

>>> a.extend([4,5])

>>> id(a)

1353827822336

 

 

 

 

4.

A= [20,55,67,82,45,33,90,87,100,25]

sum = 0

for i in A:

    if i >= 50:

       sum += i

print(sum)#481

 

5.

def fibo1(n):

    if n == 0 : return 0

    elif n == 1: return 1

    else:

        return fibo1(n-1) +fibo1(n-2)

 

for i in range(10):

print(fibo1(i))

 

6.

user_input = input("숫자를 입력하여 주십시요.")

# 65,45,2,3,45,8

user_input = user_input.split(",")

sum = 0

for i in user_input:

    sum += int(i)

print(sum)

 

7.

user_input = int(input("숫자를 입력하여 주십시요."))

for i in range(1,10):

print(i * user_input,end =" ")

 

8.

f = open("abc.txt",'r')

lines = f.readlines()

f.close()

 

lines.reverse()

 

f = open("abc.txt",'w')

for line in lines:

    line = line.strip()

    f.write(line)

    f.write('\n')

f.close()

 

9.

f = open("sample.txt",'r')

lines = f.readlines()

f.close()

 

f = open("result.txt",'w')

sum = 0

for i in lines:

    sum += int(i)

f.write(str(sum/len(lines)))

f.close()

 

10.

>>> class Calculator():

    def __init__(self,numberlist):

        self.numberlist = numberlist

    def sum(self):

        result = 0

        for num in self.numberlist:

            result += num

        return result

    def avg(self):

        total = self.sum()

        return total/len(self.numberlist)

 

>>> cal1 = Calculator([1,2,3,4,5])

>>> cal1.sum()

15

>>> cal1.avg()

3.0

>>> cal2 = Calculator([6,7,8,9,10])

>>> cal2.sum()

40

>>> cal2.avg()

8.0

 

11.

>>> import sys

>>> sys.path.append("c:\doit")

>>> import mymod

 

12.

>>> result = 0

>>> try:

    [1,2,3][3]

    "a"+1

    4 / 0

except TypeError:

    result += 1

except ZeroDivisionError:

    result += 1

except IndexError:

    result += 1

finally:

    result += 4

 

   

>>> print(result)

5

 

 

13.

>>> a = "4546793"

>>> import re

>>> pat = re.compile("(\d{3})(\d{2})(\d{1})(\d{1})")

>>> print(pat.sub("\g<1>-*\g<2>-\g<3>-\g<4>",a))

454-*67-9-3

 

14.

문자열 압축하기

>>> def compress_string(s):

    _c = ""

    cnt = 0

    result =""

    for c in s:

        if c!= _c:

            _c = c

            if cnt :result += str(cnt)

            result += c

            cnt = 1

        else:

            cnt +=1

    if cnt : result += str(cnt)

    return result

 

>>> print(compress_string("aaabbcccccca"))

a3b2c6a1

 

15.

>>> def chkDupNum(s):

    result = []

    for num in s:

        if num not in result:

            result.append(s)

        else:

            return false

    return len(result) == 10

 

>>> print(chkDupNum("0123456789"))

True

>>> print(chkDupNum("01234"))

False

>>> print(chkDupNum("01234567890"))

False

>>> print(chkDupNum("6789012345"))

True

>>> print(chkDupNum("012322456789"))

False

 

16.

>>> dic = {".-":"A","-...":"B","-.-.":"C","-..":"D",".":"E","..-.":"F","--.":"G"

       ,"....":"H","I":"..",".---":"J","-.-":"K",".-..":"L","--":"M","-.":"N"

       ,"---":"O",".--.":"P","--.-":"Q",".-.":"R","...":"S","-":"T"

       ,"..-":"U","...-":"V",".--":"W","-..-":"X","-.--":"Y","--..":"Z"}

>>> def morse(src):

    result = []

    for word in src.split(" "):

        for char in word.split(" "):

            result.append(dic[char])

        result.append(" ")

    return "".join(result)

 

>>> print(morse(".... ... .-.. . . .--. ... . .- .-.. -.--"))

H S L E E P S E A L Y

 

17.

>>> import re

>>> p = re.compile("a[.]{3,}b")

>>> print(p.search("acccb"))

None

>>> print(p.search("a....b"))

<re.Match object; span=(0, 6), match='a....b'>

>>> print(p.search("aaab"))

None

>>> print(p.search("a.cccb"))

None

 

18.

>>> import re

>>> p = re.compile("[a-z]+")

>>> m = p.search("5 python")

>>> m.start()+m.end()

10

>>> m.start()

2

>>> m.end()

8

 

19.

>>> data = """

park 010-9999-9988

kim 010-9909-7789

lee 010-8789-7768

"""

>>> import re

>>> p = re.compile("(\d{3}[-]+\d{4}[-])\d{4}")

>>> print(p.sub(r"\g<1>-####",data))

 

park 010-9999--####

kim 010-9909--####

lee 010-8789--####

 

20.

>>> import re

>>> pat = re.compile(".*[@].*[.](?=com$|net$).*$")

>>> print(pat.match("pankey@gmail.com"))

<re.Match object; span=(0, 16), match='pankey@gmail.com'>

>>> print(pat.match("kim@daum.com"))

<re.Match object; span=(0, 12), match='kim@daum.com'>

>>> print(pat.match("lee@myhome.com"))

<re.Match object; span=(0, 14), match='lee@myhome.com'>

반응형

'Study > Python' 카테고리의 다른 글

Python-9  (0) 2020.09.12
python-8  (0) 2020.09.12
python-6  (0) 2020.09.10
python-5  (0) 2020.09.09
python-4  (0) 2020.09.08

+ Recent posts