Java의 IO 재사용에 대한 자세한 그래픽 및 텍스트 설명
이 기사는 주로 Java IO 재사용에 대한 관련 지식을 소개합니다. 매우 훌륭하고 참조할 가치가 있습니다. 필요한 친구가 참조할 수 있습니다.
서버의 동시 처리 기능을 위해 필요한 것은: 매 밀리초입니다. 이 밀리초 내에 수백 개의 서로 다른 TCP 연결을 통해 수신된 모든 메시지는 적시에 처리될 수 있습니다. 동시에 서버에는 메시지를 보내거나 받지 않은 상대적으로 비활성 연결이 수십만 개 있을 수 있습니다. 지난 몇 초 동안. 동시에 이벤트가 발생하는 여러 연결을 처리하는 것을 줄여서 수만 또는 수십만 개의 연결을 동시에 처리하는 것을 동시성이라고 합니다. 서버 동시성programming이 추구하는 것은 물리적 자원이 먼저 소진될 때까지 CPU 등의 자원을 효율적으로 사용하면서 무한한 동시 연결을 처리하는 것입니다.
동시 프로그래밍모델에는 많은 구현이 있으며, 가장 간단한 것은 "스레드"와 함께 번들로 제공되며, 1개의 스레드가 1개의 연결의 전체 수명주기를 처리합니다. 장점: 이 모델은 충분히 간단하고 복잡한 비즈니스 시나리오를 구현할 수 있으며 동시에 스레드 수가 CPU 수보다 훨씬 클 수 있습니다. 그런데 스레드 수를 무한정 늘릴 수는 없습니다. 이유는 무엇입니까? 스레드가 실행될 때 운영 체제 커널 스케줄링 알고리즘에 의해 결정되기 때문에 스케줄링 알고리즘은 특정 스레드가 하나의 연결만 제공할 수 있다는 것을 고려하지 않습니다. 즉, 타임 슬라이스가 종료되더라도 실행됩니다. 이 스레드가 실행되면 계속해서 잠을 자야 합니다. 이렇게 스레드를 깨우고 휴면 상태로 왔다갔다하는 것은 횟수가 적을 때 저렴하지만, 운영 체제의 전체 스레드 수가 많으면 비용이 많이 듭니다(증폭). 이러한 기술적인 스케줄링 손실이 스레드에 영향을 미치기 때문입니다. 비즈니스 코드가 실행되는 시간입니다. 예를 들어, 현재 연결이 활성화되지 않은 대부분의 스레드는 우리 국영 기업과 같으며 실행 효율성이 너무 낮습니다. 즉, 활성 연결을 처리하는 민간 기업 스레드 수가 줄어들고 CPU를 확보할 기회가 줄어듭니다. CPU는 핵심 경쟁력이며 CPU의 비효율성은 전체 GDP 처리량에 영향을 미칩니다. 우리가 추구하는 것은 수십만 개의 연결을 동시에 처리하는 것입니다. 수천 개의 스레드가 나타나면 시스템의 실행 효율성은 더 이상 높은 동시성을 충족할 수 없습니다.
고동시성 프로그래밍에는 현재 단 하나의 모델만 있으며 이는 본질적으로 유일한 효과적인 방법입니다. 연결에 대한 메시지 처리는 메시지가 준비될 때까지 기다리는 단계와 메시지 처리라는 두 단계로 나눌 수 있습니다. 기본 차단 소켓(예: 위에서 언급한 하나의 연결을 처리하기 위해 하나의 스레드가 번들로 제공됨)을 사용하는 경우 이러한 두 단계가 하나로 결합되는 경우가 많기 때문에 소켓 코드를 작동하는 스레드는 메시지가 준비될 때까지 대기해야 합니다. , 이로 인해 스레드가 높은 동시성에서 자주 절전 모드로 전환되어 CPU 사용 효율성에 영향을 미칩니다.
고동시성 프로그래밍 방식은 물론 두 단계를 분리하는 것입니다. 즉, 메시지가 준비될 때까지 기다리는 코드 섹션이 메시지를 처리하는 코드 섹션과 분리됩니다. 물론 이를 위해서는 소켓이 비차단 상태여야 합니다. 그렇지 않으면 메시지를 처리하는 코드 세그먼트로 인해 조건이 충족되지 않을 때 스레드가 절전 대기 단계에 쉽게 들어갈 수 있습니다. 그렇다면 문제는 메시지가 준비될 때까지 기다리는 이 단계를 어떻게 달성할 것인가 하는 것입니다. 결국, 여전히 대기 중입니다. 이는 스레드가 여전히 휴면 상태에 있어야 함을 의미합니다! 해결책은 적극적으로 query하거나 1개의 스레드가 모든 연결을 기다리도록 하는 것입니다! 이것이 IO 멀티플렉싱입니다. 멀티플렉싱은 메시지가 준비될 때까지 기다리는 것이지만 동시에 여러 연결을 처리할 수 있습니다! "대기"할 수도 있으므로 스레드를 절전 모드로 전환할 수도 있지만 일대다 방식이고 모든 연결을 모니터링할 수 있으므로 문제가 되지 않습니다. 이러한 방식으로 스레드가 실행을 위해 깨어날 때 코드에서 실행할 준비가 된 일부 연결이 있어야 하며 이는 효율적입니다! "메시지 준비 대기" 단계를 처리하기 위해 경쟁하는 스레드가 그리 많지 않으며 마침내 전 세계가 명확해졌습니다!
다중화 구현이 많이 있습니다. linux에서는 2.4 커널 이전에는 선택 및 폴링이 주요 구현이었습니다. 이제 사용 방법은 매우 다른 것처럼 보이지만 본질은 동일합니다.
효율성도 다르기 때문에 epoll이 select를 완전히 대체한 것입니다.
epoll이 select를 대체하는 이유에 대해 간단히 이야기해 보겠습니다.
앞서 언급했듯이 높은 동시성을 위한 핵심 솔루션은 모든 연결에 대해 "메시지가 준비되기를 기다리는 중"을 하나의 스레드로 처리하는 것입니다. 이 점에서 epoll과 select는 논란의 여지가 없습니다. 그러나 선택 추정에서 한 가지 잘못된 점은 첫 번째 장에서 말했듯이 수십만 개의 동시 연결이 존재하는 경우 밀리초마다 수백 개의 활성 연결만 있을 수 있고 나머지 수십만 개의 연결이 활성화될 수 있습니다. 밀리초는 비활성 상태입니다. select를 사용하는 방법은 다음과 같습니다. 반환된 활성 연결 ==select(모니터링할 모든 연결)
select 메소드는 언제 호출되나요? 패킷이 도착한 활성 연결을 찾아야 한다고 생각되면 이 호출을 호출해야 합니다. 따라서 동시성이 높을 때 select 호출이 자주 호출됩니다. 이처럼 자주 호출되는 방법이 "자주"라는 단어로 인해 약간의 효율성 손실이 증폭되기 때문에 효율적인지 여부를 확인할 필요가 있습니다. 효율성 손실이 있습니까? 분명히 모니터링할 연결은 수십만 개인데 활성 연결은 수백 개만 반환되므로 그 자체로는 비효율적입니다. 증폭된 후에는 select가 수만 개의 동시 연결을 완전히 처리할 수 없다는 것을 알게 될 것입니다.
사진 몇 장을 보세요. 동시 연결 수가 1,000개 미만인 경우 select 실행 횟수가 빈번하지 않으며 epoll과 큰 차이가 없는 것 같습니다.
그러나 동시 연결 수가 증가하면 select의 단점은 "잦은 실행"으로 인해 무한히 확대됩니다. 그리고 동시성이 많을수록 더 분명해집니다.
epoll이 이를 어떻게 해결하는지 이야기해 보겠습니다. 3가지 방법을 교묘하게 사용하여 select 방법이 수행하는 작업을 수행합니다.
New epoll descriptor==epoll_create()
epoll_ctrl(epoll 설명자, 모니터링할 모든 연결을 추가 또는 삭제)
반환된 활성 연결 == epoll_wait(epoll 설명자)
이 작업의 주요 이점은 자주 호출되는 작업과 자주 호출되지 않는 작업을 구별하는 것입니다. 예를 들어 epoll_ctrl은 덜 자주 호출되는 반면 epoll_wait는 매우 자주 호출됩니다. 이때 epoll_wait에는 매개변수가 거의 없어 select보다 훨씬 효율적입니다. 또한 동시 연결 수가 증가해도 매개변수 수를 늘리지 않아 커널 실행 효율성이 저하됩니다.
epoll은 어떻게 구현되나요? 실제로 epoll_wait가 "어떤 연결이 이미 메시지 준비에 있는지" 자주 호출할 때마다 모니터링할 모든 연결을 전달할 필요가 없다는 점에서 이 세 가지 방법에서 더 똑똑하다는 것을 알 수 있습니다. 무대". of. 이는 모니터링할 모든 연결을 저장하기 위해 커널 모드에서 데이터 구조를 유지한다는 의미입니다. 이 데이터 구조는 레드-블랙 트리이며, 해당 노드의 추가 및 감소는 epoll_ctrl을 통해 완료됩니다. 매우 간단합니다.
그림 왼쪽 하단의 빨간색-검은색 트리는 모니터링할 모든 연결로 구성됩니다. 왼쪽 상단의 연결 목록에는 현재 활성화된 모든 연결이 표시됩니다. 따라서 epoll_wait가 실행되면 왼쪽 상단 연결 리스트만 확인하고 왼쪽 상단 연결 리스트에 있는 연결을 사용자에게 반환합니다. 이런 식으로 epoll_wait의 실행 효율성이 낮아질 수 있나요?
마지막으로 epoll에서 제공하는 두 가지 게임 플레이 방법인 ET와 LT, 즉 번역된 Edge Trigger와 수평 Trigger를 살펴보겠습니다. 사실 이 두 중국어 이름은 어느 정도 적절하다. 이 두 가지 사용 방법은 여전히 효율성 문제를 목표로 하고 있지만 단지 epoll_wait에서 반환된 연결을 더 정확하게 만드는 방법이 될 뿐입니다.
예를 들어, 연결의 쓰기 버퍼가 사용 가능한지 여부를 모니터링해야 합니다. "쓰기 가능"하면 사용자 모드에서 클라이언트에 응답 호출 쓰기를 보낼 수 있습니다. 그러나 연결이 쓰기 가능한 경우에도 "응답" 콘텐츠가 여전히 디스크에 남아 있을 수 있습니다. 이때 디스크 읽기가 완료되지 않은 경우 어떻게 될까요? 스레드가 차단되어서는 안 되므로 응답이 전송되지 않습니다. 다만, 다음 번 epoll_wait 시 연결이 반환될 수 있으므로 이를 처리할지 여부를 확인해야 합니다. 아마도 우리 프로그램에는 디스크 IO를 특별히 처리하는 또 다른 모듈이 있을 수 있으며, 디스크 IO가 완료되면 응답을 보낼 것입니다. 그렇다면 epoll_wait는 즉시 처리할 수 없는 "쓰기 가능한" 연결을 반환합니까? 사용자 기대에 부응합니까?
그래서 ET와 LT 모드가 탄생하게 되었습니다. LT는 예상되는 상태를 충족하는 모든 연결이 epoll_wait에서 반환되어야 하므로 모든 사람을 동등하게 취급하고 수평선에 있음을 의미합니다. 보다 정확한 리턴 연결을 선호하는 ET의 경우는 그렇지 않습니다. 위의 예에서 연결이 처음으로 쓰기 가능하게 된 후 프로그램이 연결에 데이터를 쓰지 않으면 epoll_wait는 다음 번에 연결을 반환하지 않습니다. ET를 에지 트리거라고 합니다. 이는 연결이 한 상태에서 다른 상태로 변경될 때만 epoll_wait가 트리거되어 이를 반환한다는 것을 의미합니다. ET의 프로그래밍은 훨씬 더 복잡하다는 것을 알 수 있습니다. 최소한 애플리케이션은 epoll_wait에 의해 반환된 연결이 나타나지 않도록 주의해야 합니다. 쓰기 가능한 경우 데이터는 기록되지 않지만 다음 "쓰기 가능"을 예상합니다. 읽을 수 있으면 데이터를 읽지 않고 다음 번에 "읽을 수 있게" 됩니다.
물론 일반 애플리케이션 시나리오에서는 성능에 큰 차이가 없습니다. ET의 가능한 장점은 epoll_wait에 대한 호출 수가 줄어들고 일부 시나리오에서는 연결이 해제되지 않는다는 것입니다. 필요하지 않습니다(이 Wake-up은 epoll_wait 반환을 참조함). 하지만 위에서 언급한 예와 같은 경우에는 단순한 네트워크 문제가 아니라 응용 시나리오와 관련된 경우도 있습니다. 물론 대부분의 오픈 소스 프레임워크 는 ET를 기반으로 작성되었으며 프레임워크는 순전히 기술적인 문제를 추구하며 완벽함을 위해 노력합니다
위 내용은 Java의 IO 재사용에 대한 자세한 그래픽 및 텍스트 설명의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

핫 AI 도구

Undresser.AI Undress
사실적인 누드 사진을 만들기 위한 AI 기반 앱

AI Clothes Remover
사진에서 옷을 제거하는 온라인 AI 도구입니다.

Undress AI Tool
무료로 이미지를 벗다

Clothoff.io
AI 옷 제거제

Video Face Swap
완전히 무료인 AI 얼굴 교환 도구를 사용하여 모든 비디오의 얼굴을 쉽게 바꾸세요!

인기 기사

뜨거운 도구

메모장++7.3.1
사용하기 쉬운 무료 코드 편집기

SublimeText3 중국어 버전
중국어 버전, 사용하기 매우 쉽습니다.

스튜디오 13.0.1 보내기
강력한 PHP 통합 개발 환경

드림위버 CS6
시각적 웹 개발 도구

SublimeText3 Mac 버전
신 수준의 코드 편집 소프트웨어(SublimeText3)

Java 8은 스트림 API를 소개하여 데이터 컬렉션을 처리하는 강력하고 표현적인 방법을 제공합니다. 그러나 스트림을 사용할 때 일반적인 질문은 다음과 같은 것입니다. 기존 루프는 조기 중단 또는 반환을 허용하지만 스트림의 Foreach 메소드는이 방법을 직접 지원하지 않습니다. 이 기사는 이유를 설명하고 스트림 처리 시스템에서 조기 종료를 구현하기위한 대체 방법을 탐색합니다. 추가 읽기 : Java Stream API 개선 스트림 foreach를 이해하십시오 Foreach 메소드는 스트림의 각 요소에서 하나의 작업을 수행하는 터미널 작동입니다. 디자인 의도입니다

PHP는 서버 측에서 널리 사용되는 스크립팅 언어이며 특히 웹 개발에 적합합니다. 1.PHP는 HTML을 포함하고 HTTP 요청 및 응답을 처리 할 수 있으며 다양한 데이터베이스를 지원할 수 있습니다. 2.PHP는 강력한 커뮤니티 지원 및 오픈 소스 리소스를 통해 동적 웹 컨텐츠, 프로세스 양식 데이터, 액세스 데이터베이스 등을 생성하는 데 사용됩니다. 3. PHP는 해석 된 언어이며, 실행 프로세스에는 어휘 분석, 문법 분석, 편집 및 실행이 포함됩니다. 4. PHP는 사용자 등록 시스템과 같은 고급 응용 프로그램을 위해 MySQL과 결합 할 수 있습니다. 5. PHP를 디버깅 할 때 error_reporting () 및 var_dump ()와 같은 함수를 사용할 수 있습니다. 6. 캐싱 메커니즘을 사용하여 PHP 코드를 최적화하고 데이터베이스 쿼리를 최적화하며 내장 기능을 사용하십시오. 7

PHP와 Python은 각각 고유 한 장점이 있으며 선택은 프로젝트 요구 사항을 기반으로해야합니다. 1.PHP는 간단한 구문과 높은 실행 효율로 웹 개발에 적합합니다. 2. Python은 간결한 구문 및 풍부한 라이브러리를 갖춘 데이터 과학 및 기계 학습에 적합합니다.

PHP는 특히 빠른 개발 및 동적 컨텐츠를 처리하는 데 웹 개발에 적합하지만 데이터 과학 및 엔터프라이즈 수준의 애플리케이션에는 적합하지 않습니다. Python과 비교할 때 PHP는 웹 개발에 더 많은 장점이 있지만 데이터 과학 분야에서는 Python만큼 좋지 않습니다. Java와 비교할 때 PHP는 엔터프라이즈 레벨 애플리케이션에서 더 나빠지지만 웹 개발에서는 더 유연합니다. JavaScript와 비교할 때 PHP는 백엔드 개발에서 더 간결하지만 프론트 엔드 개발에서는 JavaScript만큼 좋지 않습니다.

PHP와 Python은 각각 고유 한 장점이 있으며 다양한 시나리오에 적합합니다. 1.PHP는 웹 개발에 적합하며 내장 웹 서버 및 풍부한 기능 라이브러리를 제공합니다. 2. Python은 간결한 구문과 강력한 표준 라이브러리가있는 데이터 과학 및 기계 학습에 적합합니다. 선택할 때 프로젝트 요구 사항에 따라 결정해야합니다.

캡슐은 3 차원 기하학적 그림이며, 양쪽 끝에 실린더와 반구로 구성됩니다. 캡슐의 부피는 실린더의 부피와 양쪽 끝에 반구의 부피를 첨가하여 계산할 수 있습니다. 이 튜토리얼은 다른 방법을 사용하여 Java에서 주어진 캡슐의 부피를 계산하는 방법에 대해 논의합니다. 캡슐 볼륨 공식 캡슐 볼륨에 대한 공식은 다음과 같습니다. 캡슐 부피 = 원통형 볼륨 2 반구 볼륨 안에, R : 반구의 반경. H : 실린더의 높이 (반구 제외). 예 1 입력하다 반경 = 5 단위 높이 = 10 단위 산출 볼륨 = 1570.8 입방 단위 설명하다 공식을 사용하여 볼륨 계산 : 부피 = π × r2 × h (4

phphassignificallyimpactedwebdevelopmentandextendsbeyondit

PHP가 많은 웹 사이트에서 선호되는 기술 스택 인 이유에는 사용 편의성, 강력한 커뮤니티 지원 및 광범위한 사용이 포함됩니다. 1) 배우고 사용하기 쉽고 초보자에게 적합합니다. 2) 거대한 개발자 커뮤니티와 풍부한 자원이 있습니다. 3) WordPress, Drupal 및 기타 플랫폼에서 널리 사용됩니다. 4) 웹 서버와 밀접하게 통합하여 개발 배포를 단순화합니다.
