2016-10-05 5 views
1

나는 다중 스레드 웹 서버를 작성 중이며 기본적으로 서버 시작시 복수 스레드에 사용자 제공 처리기 객체 인 Vec<Handler>을 복사해야합니다. 몇 가지 접근 방식을 시도 : fn process(&mut self, Request) -> Response 메서드와 함께 특성으로 처리기를 정의하십시오 :어떻게 스레드간에 핸들러를 공유합니까?

1) 핸들러를 정의하십시오. 사용자는 각 핸들러 구조체에 대해이를 구현합니다. 이 방법은 C++이나 python과 같은 언어에서 매우 일반적입니다. 문제는 녹이 특성 개체에 대해 금지 된 Sized이 바인딩 된 것을 의미하므로 특성 개체를 복사하거나 복제 할 수 없다는 것입니다.

2) 핸들러를 Box<FnMut(Request) -> Response>으로 정의하십시오. 클로저는 카피 할 수 없기 때문에 이것은 동작하지 않습니다.

3) 스레드간에 동일한 개체를 공유 할 수 있지만 실제로는 스레드간에 별도의 복사본이 필요할 때 쓸모없는 경합이 발생하는 뮤텍스가 필요하므로이 점이 저에게 거의 의미가 없습니다.

어떻게 올바르게 구현할 수 있습니까?

답변

1

가장 간단한 해결책은 사용자에게 복제 방법을 정의하도록 요청하는 것입니다.

trait Handler { 
    fn process(&mut self, r: Request) -> Response; 
    fn duplicate(&self) -> Box<Handler>; 
} 

그리고 나서 Vec<Box<Handler>>을 매우 쉽게 복사 할 수 있습니다.

+0

제안 해 주셔서 감사합니다. 불행히도 스레드와 잘 작동하지 않는 것 같습니다. 주어진 스레드가 상자 을 소유하고 있지만 Handler가 Send를 구현해야 함을 의미하는 Handler를 소유하지 않습니다. Rust는 Handler 객체가 스레드 외부의 참조를 가지고 있지 않음을 알 수 없습니다. 이렇게하면 Handler 스레드를 안전하게 만듭니다. – ElefEnt

+0

복사와 쓰레드 안전은 다른 이슈들입니다. 실제로 핸들러를 쓰레드로 보내기를 원한다면'Handler'에 바인드 된'Send'를 추가하거나 (''static'' 바운드도 될 수 있습니다) 추가 할 수 있습니다 상자에'Box '와 같이 입력한다. 편의상 나는 전자를 추천 할 것이다. –

+0

이 메소드의 이름을 'clone'으로 지정하면 혼란 스러울 수 있습니다. – mcarton

관련 문제