2020年1月24日金曜日

Python의 Sanic 프레임 워크는 초당 몇 건의 DATA 처리가 가능합니까?





 페이지를 보면 알 수 있습니다. JSON serialization에서 초당 283,645 개입니다.

그러나 그 숫자는 현실적으로 거의 의미가 없습니다.

먼저 일반적인 Web 서버는 사용자 인증, 데이터베이스 액세스, HTML의 작성 등의 작업을하기 때문에 그 처리 시간이 훨씬 길어집니다. 단순히 Sanic의 처리 시간은 무시할 수 단순히 것입니다.

또한 Web 응용 프로그램에서 초당 1000 건 이상 처리해야하는 경우는 그다지 없습니다. 먼저 Niginx 등의 Web 서버 쪽에서 정적 파일 동작이나 캐시가 가능합니다. 이렇게 해두면, 직원 1 만명의 회사의 사내 시스템에서 초당 1000 개의 처리가 필요한 경우는 적습니다.

지금도 Dgango과 Flask가 주로 사용되고있는 것은, 일반적으로 그것으로 충분한 경우가 많기 때문입니다. 그래서 문제가있는 경우에는 Python으로 Sanic를 사용하는 것보다 일반적으로 속도가 빨라 병렬 처리 기능을 갖추고있는 Go 언어를 사용하는 것이 더 나은 사례가 많다고 생각합니다. 또한 여기서 말하고있는 것은 Sanic를 사용하지 말라는 것이 아니라 초당 처리 건수가 많은 경우에는 그 처리는 Python 자체가 적합하지 않을 수 많다는 뜻입니다 .
조회수 : 80 회 · 이시즈카 마사히로 씨가 요청한 답변
높은 평가
공유



추천
모든

답변 고마워요 있습니다.
> Python으로 Sanic를 사용하는 것보다 일반적으로 속도가 빨라 병렬 처리 기능을 갖추고있는 Go 언어를 사용하는 것이 더 나은 사례가 많다고 생각합니다.

과연 총


정리

  •  의 GIL가 멀티 스레드를 사용해도 멀티 코어의 혜택을하지 않도록하고있다.

여기 블로그가 맞으면 함께 고려하면, Python은 멀티 코어 CPU를 살릴 수 프로그램 언어라고 말하게됩니다. AI (인공 지능)과 기계 학습 라이브러리를 필요로하지 않는다면, Python보다 Go lang 쪽이 우수하고 있지만, Go lang 위해 AI (인공 지능)과 기계 학습 라이브러리가 충실하거나 Python 와 프레임 워크에서 멀티 코어 CPU를 정식으로 지원 해 나갈까 중 하나가 앞으로 이루어지고 해결해 나갈 것을기도하고 있습니다. 또한 Go lang 용으로도 TensorFlow라고 Google에서 개발 한 AI, 기계 학습, 수치 해석 라이브러리가 있습니다. Go lang에서도이 API를 사용할 수 있지만, 아직은 모델 구축, 학습 할 수있는 것은 Python 만 같기 때문에 향후 개선 될 것을 희망합니다.
회신


GIL의 건입니다 만, 무거운 처리를 C / C ++로 작성하거나 C / C ++로 작성된 라이브러리를 사용하면 분리 할 수 있기 때문에, 보통은 문제가되지 않습니다. 그러나 초당 처리 건수가 매우 많은 양이 될 것으로 처리 충돌을 피할 수 없게되므로, Python에서는 효율이 나빠져 버립니다. 그래서 Go 쪽을 사용하도록 권장하고있을뿐입니다. 큰 것이어야, Python만으로 개발해도 문제가되지 않습니다. 큰 경우에는 Python만으로 견딜 수 있는지 계산 및 테스트가 필요하다고 생각합니다.

기계 학습에 관해서는 훈련 분들은 대량의 데이터를 사용하여 대량의 계산을합니다. 이것에 관해서는, Python에 익숙하지 Go는 약해서, Go에서 기계 학습 모델 구축, 학습을 할 수있게되는 것은 당분간 없습니다.

한편, 학습 한 결과를 사용한 처리에서는 결과를 사용할 뿐이므로 계산에 대해서는 가벼운 처리됩니다. 만약 여기에서 대량의 처리 건수를 오지 않음 않으면 안한다면 위에 언급 이유로 Go 쪽이 적합하므로, Go위한 API가 있다는 뜻입니다.

TesorFlow도 Go도 Google에서 개발 한 것이지만, Python과 Go의 특성을 고려한 결과 그렇게되어 있기 때문에 단일화되는 것은 없다고 생각하는 것이 좋을 것입니다.
회신
높은 평가

질문보기
응답자의 소개

당신이 알고있는 1 명의 팔로워 야마자키 다케오

프리랜서로 근무 2013- 현재

교토 대학에서 학부를 전공

도쿠시마 현에 살았던 0-0

콘텐츠 조회수 : 344.6k 회 달 : 26.9k 시간
1 개의 공간으로 활성화

배기
Python4는 진정한 멀티 코어 및 멀티 스레드 지원합니까?
댓글 :
Python3의 블로그를 읽고 확인합니다.
혹시,
Python2 & 3는 가짜 멀티 코어 및 멀티 스레드의 위해, JAVA 나 Go lang (Go 언어)와 같은 진정한 멀티 코어 및 멀티 스레드와는 다른 것이 아니냐 확인합니다.

uvloop으로 진정한 멀티 코어 및 멀티 스레드?
말 것이 가능 할지도 모릅니다.
aon CEO 이시 마사히로
tel : 042-559-8638
iPhone : 070-3861-5011

asyncio가 POSIX 쓰레드를 사용하고있는 원인을 조사
  

공유했습니다.

tokibito 선생님 ( id : nullpobug )가 사무실에 놀러와과 말을 걸어 주었으므로, 오픈 수집가 씨에 놀러 가고있었습니다. aodag 선생님 ( id : aodag )와 3 명이 서 잡담하고 있었던 것입니다 만, 문득 이전 궁금했던 것을 기억 때문에 물어 보았다.

신경이 쓰여 있었다

어떤 연구회의 발표 자료 를 만들고있을 때, asyncio과 aiohttp를 사용하여 어떤 서버에 HTTP 요청을 보내는 코드 예제를 마련했다.
  import aiohttp
 import asyncio

 async def fetch (l, url) :
     async with aiohttp.ClientSession (loop = l) as session :
         async with session.get (url) as response :
             return await response.text ()


 async def main (l, url, num) :
     tasks = fetch (l, url) for _ in range (num)
     return await asyncio.gather (* tasks)


 if __name__ == '__main__':
     loop = asyncio.get_event_loop ()
     results = loop.run_until_complete (main (loop 'http : // localhost : 8000', 3))
     for r in results :
         print (r)
PyCharm는 "Concurrency Diagram"을 표시하는 기능이 있고, 스레드 및 프로세스의 움직임을 확인 할 수 있습니다 만,이 코드를 실행했을 때의 스레드의 움직임은 다음과 같다.
f : id : nwpct1 : 20170330234242p : plain
왠지 concurrent.futures.ThreadPoolExecutor 이 나타나고있다. 문서에 무엇인가 써 있는지 알아 보았습니다 만, 그럴듯한 설명을 찾지 못하고 단념하고 있었으므로 aodag 선생님과 tokibito 선생님에게 물어 보았다.

socket.getaddrinfo

수십 분에서 원인을 찾아 주었다. socket.getaddrinfo 가 동 기적으로 실행되어 버리기 때문에 cpython의 구현은이를 비동기 적으로 수행 할 수 있도록 바꾸는 것이 아니라 일단 concurrent.futures.ThreadPoolExecutor 의해 여러 스레드에서 실행하도록하고있는 것 같다.
운동에 getaddrinfo가 사용되지 않는 코드 샘플로 aioredis 을 사용한 샘플을 준비했다. 로컬 세운 Redis 서버에 UNIX 도메인 소켓에 연결해 본다.
  import asyncio
 import aioredis

 async def connection_example (key) :
     conn = await aioredis.create_connection ( '/tmp/redis.sock')
     return await conn.execute ( 'GET', key)


 async def main (num) :
     tasks = [connection_example ( 'my-key') for _ in range (num)
     return await asyncio.gather (* tasks)


 if __name__ == '__main__':
     loop = asyncio.get_event_loop ()
     results = loop.run_until_complete (main (3))
     for r in results :
         print (r)
덧붙여서 redis의 config는 ↓.
  daemonize no
 pidfile /var/run/redis.pid
 unixsocket /tmp/redis.sock
 unixsocketperm 700
 logfile ""
 databases 1 
이때 Concurrency Diagram을 보면,
f : id : nwpct1 : 20170331163806p : plain
분명히 스레드가 생성되지 않는다.
외부 Redis 서버에 액세스
한편 Redis 서버를 외부에 제공하고 연결해 보면 (이번은 arukas.io 을 사용하게 해 주셨습니다)
  import asyncio
 import aioredis

 async def connection_example (key) :
     conn = await aioredis.create_connection (
         ( 'seaof-xxx-xxx.arukascloud.io', 311390)
         db = 0, password = 'xxxxxxxxxxxxxxx')
     return await conn.execute ( 'GET', key)


 async def main (num) :
     tasks = [connection_example ( 'my-key') for _ in range (num)
     return await asyncio.gather (* tasks)


 if __name__ == '__main__':
     loop = asyncio.get_event_loop ()
     results = loop.run_until_complete (main (3))
     for r in results :
         print (r)
실행하면 다음과 같다.
f : id : nwpct1 : 20170331163620p : plain
오 역시 작업자 스레드가 생성되어 버리는 것 같다.

ThreadPoolExecutor 작업자 스레드는 몇 개까지 생성되는지.

Semaphore에서 동시에 실행될 수를 3 개로 제한했을 때의 Concurrency Diagram은 다음과 같다.
f : id : nwpct1 : 20170331164208p : plain
아무래도 ThreadPoolExecutor 내의 Thread가 재사용되지 않는다. 어디까지 생성되는지는 문서의 ThreadPoolExecutor의 곳에 써 있었다.
max_workers가 None 또는 지정되지 않은 경우 기본값은 컴퓨터의 프로세서 수에 5를 곱한 것입니다
17.4 concurrent.futures - 병렬 작업 실행 - Python 3.6.1 문서
시도에 30 개 정도 요청을 보내 본다 (Semaphore 3).
f : id : nwpct1 : 20170331164432p : plain
20 개까지 생성되고 그 이후에는 재사용되는 것을 확인할 수 있었다. 구현에 작업자 스레드 한계는 변경할 수 없지만, 분명히 따로 곤란한 경우도 없을 것.

uvloop

uvloop 분은 POSIX 스레드없이 노력하고지도하는 이야기가 나왔으므로 확인.
  import uvloop

 # 중략
 loop = uvloop.new_event_loop ()
 asyncio.set_event_loop (loop)
실행하면
f : id : nwpct1 : 20170330232815p : plain
오 정말이다.

결론

aodag 선생님과 tokibito 선생님 대단 ... 자신은 문서를 읽으면서 답답 채 방치하고 만 수십 분에서 원인을 찾아 가르쳐 주었다. 자신도 드디어 내일부터 사회인이므로 두분 목표로 정진하고 있습니다.
aodag 선생님과 tokibito 선생님이있는 오픈 수집가 씨, 일 모집 중이라고합니다 (신세를 진 때문에 한마디 선전). 감사합니다!

0 コメント:

コメントを投稿