मैं निम्नलिखित वर्ग परिभाषाएं हैं कहते हैं:सर्वश्रेष्ठ अभ्यास/इंतजार
public class Calculator
{
public CalculatorResult Calculate()
{
return LongRunningCalculation();
}
private CalculatorResult LongRunningCalculation()
{
return new CalculatorResult(0.00);
}
}
public class ClassThatUsesACalculator
{
private readonly Calculator calculator;
public ClassThatUsesACalculator()
{
this.calculator = new Calculator();
}
public void DoWork()
{
for (int i = 0; i < 10; i++)
{
var result = calculator.Calculate();
DoSomethingWithCalculationResult(result);
DoLightWork();
OnProgressChanged();
}
}
}
public partial class Form : Form
{
public Form()
{
InitializeComponent();
}
private void Method(object sender, EventArgs e)
{
DoWork();
}
private void DoWork()
{
var calculator = new ClassThatUsesACalculator();
calculator.ProgressChanged += (s, e) =>
{
// Update progressbar
};
calculator.DoWork();
}
}
मैं फार्म पर, काम DoWork()
में किया क्या करना चाहते हैं, तो एसिंक्रोनस रूप से मैं एक विधि जोड़ सकते हैं (GetCalculationTask
) जो Task.Run()
का उपयोग करके एक कार्य देता है और एक बटन के लिए async eventhandler यानी (MethodOne
) जोड़ें।
अगर मैं गलत हूं, तो कृपया मुझे सही करें, लेकिन मुझे लगता है कि यह एकमात्र विकल्प होगा जब ClassThatUsesACalculator
और Calculator
कक्षाएं उस लाइब्रेरी में रहती हैं जो मेरे पास नहीं है।
private Task GetCalculationTask(IProgress<CalculatorProgress> progress)
{
var calculator = new ClassThatUsesACalculator();
calculator.ProgressChanged += (s, e) =>
{
progress.Report(new CalculatorProgress(0));
};
return Task.Run(() =>
{
calculator.DoWork();
});
}
private async void MethodOne(object sender, EventArgs e)
{
IProgress<CalculatorProgress> progress = new Progress<CalculatorProgress> (UpdateProgressBar);
await GetCalculationTask(progress);
}
यदि मेरे पास लाइब्रेरी है तो मुझे लगता है कि दो और विकल्प हैं, जिनमें से एक पहले की तरह बहुत अधिक है। शायद मेरी समझ की कमी के कारण।
ClassThatUsesACalculator
पर एक विधि बनाएं जो DoWork()
विधि को समाहित करता है और फिर उसे फॉर्म पर एक असीमित विधि से कॉल करता है।
या,
एक
Task.Run()
साथCalculator
वर्ग परLongRunningCalculation()
समाहित।public Task<CalculatorResult> CalculateAsync() { return Task.Run(() => { return LongRunningCalculation(); }); }
ClassThatUsesACalculator
पर कॉल कि नव निर्मित विधि इंतजार कर रहा है एक async विधि बनाएँ।public async Task DoWorkAsync() { for (int i = 0; i < 10; i++) { var result = await calculator.CalculateAsync(); DoSomethingWithCalculationResult(result); DoLightWork(); OnProgressChanged(); } }
अब फार्म पर एक अतुल्यकालिक विधि (
MethodThree
)private async void MethodThree(object sender, EventArgs e) { IProgress<CalculatorProgress> progress = new Progress<CalculatorProgress>(UpdateProgressBar); var calculator = new ClassThatUsesACalculator(); calculator.ProgressChanged += (s, args) => { progress.Report(new CalculatorProgress(0)); }; await calculator.DoWorkAsync(); }
बनाएं, मेरी राय में आखिरी विकल्प सबसे अच्छा होगा के रूप में मैं और अधिक नियंत्रण रहेगा। लेकिन हो सकता है कि मैं रास्ता बंद कर दूं और इस पर किसी की राय या पॉइंटर्स चाहूंगा क्योंकि मुझे केवल एसिंक का उपभोग करने के बारे में स्पष्टीकरण मिल सकता है, लेकिन वास्तव में दूसरों को उपभोग करने के तरीकों का निर्माण कैसे नहीं करना चाहिए।
आपका प्रश्न वास्तव में लंबा और अधिकतर शब्द है- यदि आप इसे जानना चाहते हैं तो संक्षेप में समझने के लिए इसे संकुचित कर सकते हैं। वैसे, त्वरित सामान के लिए, 'async' वास्तव में आवश्यक नहीं है। 'async' I/O कार्यों के लिए एक फ़ाइल, डेटाबेस या वेब सेवा तक पहुंचने के लिए बहुत अच्छा है। लेकिन गैर-आई/ओ कोड के त्वरित बिट्स चलाने के लिए ओवरहेड वास्तव में प्रदर्शन को कम कर सकता है। – mason