PDA

View Full Version : چرا ارور Cross-thread operation not valid رخ نمیده



bade saba
یک شنبه 23 آبان 1389, 22:49 عصر
سلام خدمت دوستان برنامه نویس

من در این پست (http://www.barnamenevis.org/forum/showthread.php?t=247848&highlight=thread)یه فیلم آموزشی راجب به thread دیدم و دانلود کردم بعد از نگاه کردن مثال اول این مبحث (25ThreadSample1) دیدم که با این که آموزش دهنده در فیلم از lable که در فرم هست در thread جدیدی که ایجاد میکنه استفاده میکنه اما با ارور

Cross-thread operation not valid: Control 'label1' accessed from a thread other than the thread it was created on.
برخورد نمیکنه در صورتی که من همیشه وقتی به هر دلیلی همچین چیزی در برنامم اتفاق میوفتاد این ارور رو میگره و تا اونجایی که من میدونم قاعدتا باید این ایراد گرفته بشه

ممنون میشم دوستان یه نگاهی بندازن و بگن فرق بین اون پروژه و این پروژه ای که من ضمیمه کردم چیه که پروژه من اون ایراد رو داره اما برای اون عزیز نداره. من چند بار مقایسه کردم اما تفاوتی پیدا نکردم

r00tkit
یک شنبه 23 آبان 1389, 23:34 عصر
خیلی باحاله وقتی متود start رو چند بار کلیک می کنی به تعداد کلیک ها تعداد ترید های برنامه زیاد می شه و دیگه Stop ان ها رو Stop نمی کنه ؟ اگه فهمیدید چرا

چون هر new یه ترید جدا ایجاد می کنه و t1 به جای دیگه از heap اشاره می کنه (هون جایی که در اخرین new درست شده) و stop فقط اخرین رو stop می کنه چون t1 به اخری اشاره داره حالا چی جوری قبلی ها رو stop کنیم ؟ (سی شارپ خور های عزیر برن دنبالش *از ما که گذشت*)

bade saba
یک شنبه 23 آبان 1389, 23:45 عصر
برنامه من رو دیدی؟؟؟؟
اصلا کار به چند بار کلیک کردن start نمیرسه که بخواییم در مورد stop حرف بزنیم با اولین کلیک ایرادی که نوشتم رو میگیره که به خاطر استفاده از lable هست اما تو اون برنامه اصلا ارور نمیده میشه بگی کد من موردش چیه؟؟

r00tkit
یک شنبه 23 آبان 1389, 23:55 عصر
راستش رو بخوای من اصلا" سوالت رو نخوندم فقط حدس زدم چیه و چون این مشکل فقط تو حالت دیباگ ظاهر می شه و من هم به علت کار با Windbg نمی تونم برنامه های منیج رو دیباگ کنم مشکلت رو ندیدم

برای حل مشکلت ( که هنوز هم نخوندمش ) از Invoke, BeginInvoke, EndInvoke می تونی استفاده کنی

سرچ کن corss thread تو گوگل

Pr0grammer
دوشنبه 24 آبان 1389, 00:27 صبح
مشکل Cross Thread برنامه شما به صورت زیر حل میشه :

using System.Threading;

namespace th
{
public partial class Form1 : Form
{
double i = 0;
ThreadStart ts1;
Thread t1;
public delegate void MyDisplay();

public Form1()
{
InitializeComponent();
}

public void counter()
{
for (; ; )
this.Invoke(new MyDisplay(dMethod));
}

public void dMethod()
{
i++;
label1.Text = i.ToString();
}

private void button1_Click(object sender, EventArgs e)
{
ts1 = new ThreadStart(counter);
t1= new Thread(ts1);

t1.Start();

}

private void button2_Click(object sender, EventArgs e)
{
t1.Abort();
}

}
}

موفق باشید/

mohsen_csharp
دوشنبه 24 آبان 1389, 00:59 صبح
بابا مشکل اینجاست که چرا تو اون فیلم آموزشی این خطای کراس تریدینگ به وجود نمیاد
من بررسی کردم ولی نمی دونم چرا تو اون فیلم آموزشی این خطا رخ نمی ده!!!

Reza_Yarahmadi
دوشنبه 24 آبان 1389, 08:10 صبح
من فيلم ها رو نگاه نكردم و نميدونم چطور توضيح داده ولي اگه دقيقا به همون نحوه عمل كرديد و به شما خطا ميده در حالي كه توي فيلم مشكلي نيست احتمالا فيلم ها قديمي هستند و با VS 2003 توضيح داده.
چون اين خاصيت (چك كردن Cross-thread) از دات نت 2 به بعد به وجود اومده.

bade saba
دوشنبه 24 آبان 1389, 12:07 عصر
من فيلم ها رو نگاه نكردم و نميدونم چطور توضيح داده ولي اگه دقيقا به همون نحوه عمل كرديد و به شما خطا ميده در حالي كه توي فيلم مشكلي نيست احتمالا فيلم ها قديمي هستند و با VS 2003 توضيح داده.
چون اين خاصيت (چك كردن Cross-thread) از دات نت 2 به بعد به وجود اومده.


نه دوست عزیز VS 2005 هستش

bade saba
دوشنبه 24 آبان 1389, 12:11 عصر
بابا مشکل اینجاست که چرا تو اون فیلم آموزشی این خطای کراس تریدینگ به وجود نمیاد
من بررسی کردم ولی نمی دونم چرا تو اون فیلم آموزشی این خطا رخ نمی ده!!!


دقیقا مشکل همینه که چرا اون این مشکل رو نداره وگرنه من استفاده از invoke رو بلدم

alipersia2006
پنج شنبه 01 تیر 1391, 18:34 عصر
دقیقا مشکل همینه که چرا اون این مشکل رو نداره وگرنه من استفاده از invoke رو بلدم

سلام
فک کنم اینطوری حل بشه



CheckForIllegalCrossThreadCalls = false;

مرتضی تقدمی
پنج شنبه 01 تیر 1391, 20:03 عصر
سلام
این روشی که می گم هرچند منطقی و خوب نیست اما خـــــــــــــب .... !
در load فرم یا قبل از start نخ CheckForIllegalCrossThreadCalls رو برابر false قرار بدید.

CheckForIllegalCrossThreadCalls = false;
موفق باشید

tooraj_azizi_1035
جمعه 02 تیر 1391, 20:24 عصر
سلام

دوستی که سوال کردید من در مورد روش حل این مشکل پاسخ می دهم:

اگر شما از multithreading برای بهبود کارایی Windows Forms application خود استفاده میکنید باید مطمئین شوید که فراخوانی هایتان به کنترل ها به روش Thread-Safe انجام شود. دستیابی به کنترل های Windows Forms به طور ذاتی Thread-Safeنیست. اگر بیش از یک Thread به کنترل شما همزمان دست پیدا می کنند ممکن است کنترل مورد نظر اجباراً در وضعیتی ناپایدار و همچنین وضعیت های دیگری مانند شرایط رقابت و بن بست ها قرار بگیرد.

باید حتماً مطمئن شوید که کنترل مورد نظر به روش Thread-Safe مورد دستیابی قرار می گیرد.

مثالی از فراخوانی نامطمئن(unsafe):


// This event handler creates a thread that calls a
// Windows Forms control in an unsafe way.
private void setTextUnsafeBtn_Click(
object sender,
EventArgs e)
{
this.demoThread =
new Thread(new ThreadStart(this.ThreadProcUnsafe));

this.demoThread.Start();
}

// This method is executed on the worker thread and makes
// an unsafe call on the TextBox control.
private void ThreadProcUnsafe()
{
this.textBox1.Text = "This text was set unsafely.";
}


با استفاده از خاصیت InvokeRequired می توان مطمئن شد که دسترسی مستقیم امکان پذیر است یا خیر:


// This method demonstrates a pattern for making thread-safe
// calls on a Windows Forms control.
//
// If the calling thread is different from the thread that
// created the TextBox control, this method creates a
// SetTextCallback and calls itself asynchronously using the
// Invoke method.
//
// If the calling thread is the same as the thread that created
// the TextBox control, the Text property is set directly.

private void SetText(string text)
{
// InvokeRequired required compares the thread ID of the
// calling thread to the thread ID of the creating thread.
// If these threads are different, it returns true.
if (this.textBox1.InvokeRequired)
{
SetTextCallback d = new SetTextCallback(SetText);
this.Invoke(d, new object[] { text });
}
else
{
this.textBox1.Text = text;
}
}



منبع :

http://msdn.microsoft.com/en-us/library/ms171728.aspx