Thread에서 ThreadStart 메서드에 매개 변수를 전달하는 방법은 무엇입니까?
를 에 전달하는 Thread.ThreadStart()
C#에 있는 방법?
'다운로드'라는 메서드가 있다고 가정합니다.
public void download(string filename)
{
// download code
}
이제 메인 메서드에서 하나의 스레드를 만들었습니다.
Thread thread = new Thread(new ThreadStart(download(filename));
오류 메서드 유형이 필요합니다.
를 매개변에방법는하에 전달하려면 해야 합니까?ThreadStart
매개 변수가 있는 대상 방법으로?
가장 간단한 것은 바로
string filename = ...
Thread thread = new Thread(() => download(filename));
thread.Start();
은 이보이점(들)보다 (들).ParameterizedThreadStart
는 여러 변수를 할 수 , 에서 없이 수 있다는 입니다.object
시종일관
이 예를 보십시오.
public void RunWorker()
{
Thread newThread = new Thread(WorkerMethod);
newThread.Start(new Parameter());
}
public void WorkerMethod(object parameterObj)
{
var parameter = (Parameter)parameterObj;
// do your job!
}
먼저 작업자 메서드에 위임자를 전달하여 스레드를 만든 다음 스레드로 시작합니다.개체를 매개 변수로 사용하는 시작 메서드입니다.
따라서 사용자의 경우에는 다음과 같이 사용해야 합니다.
Thread thread = new Thread(download);
thread.Start(filename);
그러나 '다운로드' 메서드는 여전히 매개 변수로 문자열을 사용하지 않고 개체를 사용해야 합니다.메소드 본문의 문자열에 캐스팅할 수 있습니다.
매개 변수를 사용하는 스레드 메서드에 대해 대리자를 사용하려고 합니다. (또는 실제로는 전혀 없음)Thread
생성자 추론).
사용 예:
var thread = new Thread(new ParameterizedThreadStart(download));
//var thread = new Thread(download); // equivalent
thread.Start(filename)
당신도 할 수 있습니다.delegate
그런 식으로...
ThreadStart ts = delegate
{
bool moreWork = DoWork("param1", "param2", "param3");
if (moreWork)
{
DoMoreWork("param1", "param2");
}
};
new Thread(ts).Start();
추가로
Thread thread = new Thread(delegate() { download(i); });
thread.Start();
저는 당신에게 파일이라는 다른 수업을 권하고 싶습니다.
public class File
{
private string filename;
public File(string filename)
{
this.filename= filename;
}
public void download()
{
// download code using filename
}
}
스레드 생성 코드에서 새 파일을 인스턴스화합니다.
string filename = "my_file_name";
myFile = new File(filename);
ThreadStart threadDelegate = new ThreadStart(myFile.download);
Thread newThread = new Thread(threadDelegate);
클래스에서 스레드 함수(다운로드)와 필요한 매개 변수(파일 이름)를 캡슐화하고 스레드 시작 대리자를 사용하여 스레드 함수를 실행할 수 있습니다.
public class Download
{
string _filename;
Download(string filename)
{
_filename = filename;
}
public void download(string filename)
{
//download code
}
}
Download = new Download(filename);
Thread thread = new Thread(new ThreadStart(Download.download);
이것은 어떻습니까: (아니면 이렇게 사용해도 괜찮습니까?)
var test = "Hello";
new Thread(new ThreadStart(() =>
{
try
{
//Staff to do
Console.WriteLine(test);
}
catch (Exception ex)
{
throw;
}
})).Start();
당신 질문에 따르면...
매개 변수를 스레드에 전달하는 방법.C#의 ThreadStart() 메서드?
...그리고 발생한 오류는 코드를 수정해야 합니다.
Thread thread = new Thread(new ThreadStart(download(filename));
로.
Thread thread = new Thread(new ThreadStart(download));
thread.Start(filename);
하지만, 처음에 보이는 것처럼 질문은 더 복잡합니다.
현재 클래스(4.7.2)는 오버로드가 있는 여러 생성자와 메서드를 제공합니다.
이 질문과 관련된 생성자는 다음과 같습니다.
public Thread(ThreadStart start);
그리고.
public Thread(ParameterizedThreadStart start);
대리인이나 대리인 중 한 명이 필요합니다.
해당 딜러의 모습은 다음과 같습니다.
public delegate void ThreadStart();
public delegate void ParameterizedThreadStart(object obj);
보다시피, 올바른 생성자를 사용할 수 있는 것으로 보입니다.ParameterizedThreadStart
스레드에 의해 일부 메서드가 위임자의 지정된 서명과 일치하도록 위임합니다.
인스턴스화를 위한 간단한 예Thread
수업은.
Thread thread = new Thread(new ParameterizedThreadStart(Work));
아니면 그냥
Thread thread = new Thread(Work);
해당 메서드의 서명(호출)Work
이 예에서)는 다음과 같습니다.
private void Work(object data)
{
...
}
남은 것은 스레드를 시작하는 것입니다.이 작업은 다음 중 하나를 사용하여 수행됩니다.
public void Start();
또는
public void Start(object parameter);
하는 동안에Start()
스레드를 시작하고 통과할 것입니다.null
방법에 대한 데이터로서,Start(...)
무엇이든 전달하는 데 사용될 수 있습니다.Work
나사산의 방법
그러나 이 접근 방식에는 한 가지 큰 문제가 있습니다: 모든 것이 다음과 같이 전달되었습니다.Work
메서드가 개체에 캐스팅되었습니다.즉, 내부에서Work
방법은 다음 예와 같이 원래 형식으로 다시 주조해야 합니다.
public static void Main(string[] args)
{
Thread thread = new Thread(Work);
thread.Start("I've got some text");
Console.ReadLine();
}
private static void Work(object data)
{
string message = (string)data; // Wow, this is ugly
Console.WriteLine($"I, the thread write: {message}");
}
캐스팅은 일반적으로 원하지 않는 작업입니다.
만약 누군가가 끈이 아닌 다른 것을 건네준다면요?처음에는 이것이 불가능해 보이기 때문에(나는 내 방법이기 때문에, 나는 내가 무엇을 하는지 알고 있다, 또는 그 방법은 사적인 것이다, 어떻게 누군가가 그것에게 무언가를 전달할 수 있어야 하는가?) 당신은 다양한 이유로 인해 정확하게 그 사례로 끝날 수도 있습니다.어떤 경우는 문제가 되지 않을 수도 있기 때문에 다른 경우는 문제가 됩니다.이러한 경우에는 스레드가 단순히 종료되기 때문에 눈치채지 못할 수도 있습니다.
솔루션으로 일반 제품을 구입할 수 있습니다.ParameterizedThreadStart
같은 위임을 하는.ParameterizedThreadStart<T>
어디에T
전달하고자 하는 데이터 유형이 될 것입니다.Work
방법.불행히도 이런 것은 존재하지 않습니다.
그러나 이 문제에 대한 제안된 해결책이 있습니다.여기에는 스레드에 전달될 데이터와 다음과 같은 작업자 메서드를 모두 포함하는 클래스를 만드는 작업자 메서드는 다음과 같은 작업자 메서드를 나타냅니다.
public class ThreadWithState
{
private string message;
public ThreadWithState(string message)
{
this.message = message;
}
public void Work()
{
Console.WriteLine($"I, the thread write: {this.message}");
}
}
이 방법을 사용하면 다음과 같이 스레드를 시작할 수 있습니다.
ThreadWithState tws = new ThreadWithState("I've got some text");
Thread thread = new Thread(tws.Work);
thread.Start();
따라서 이러한 방식으로 단순히 주위를 둘러보는 것을 피하고 스레드에 데이터를 안전하게 제공하는 유형의 방법을 사용할 수 있습니다;-)
여기에 완벽한 방법이 있습니다...
private void func_trd(String sender)
{
try
{
imgh.LoadImages_R_Randomiz(this, "01", groupBox, randomizerB.Value); // normal code
ThreadStart ts = delegate
{
ExecuteInForeground(sender);
};
Thread nt = new Thread(ts);
nt.IsBackground = true;
nt.Start();
}
catch (Exception)
{
}
}
private void ExecuteInForeground(string name)
{
//whatever ur function
MessageBox.Show(name);
}
언급URL : https://stackoverflow.com/questions/3360555/how-to-pass-parameters-to-threadstart-method-in-thread
'sourcecode' 카테고리의 다른 글
sed를 사용하여 문자열에서 텍스트를 추출하는 방법은 무엇입니까? (0) | 2023.05.13 |
---|---|
일반인 용어로 JSONP가 무엇인지 설명할 수 있는 사람이 있습니까? (0) | 2023.05.13 |
시작 화면 스토리보드가 이미지를 표시하지 않음 (0) | 2023.05.08 |
SDK iOS 8.0의 제품 유형 Unit Test Bundle에 대한 코드 서명 필요 (0) | 2023.05.08 |
여러 열에서 DISTINCT를 선택하려면 어떻게 해야 합니까? (0) | 2023.05.08 |