如何编写具有两个不同变量类型的参数的调用方法?
public void InsertStockPrice(double Value, string Company)
{
if (InvokeRequired)
{
Invoke(new Action<double>(InsertStockPrice), Value); // <- Not sure what to do here
}
else
{
//Do stuff
}
}
Run Code Online (Sandbox Code Playgroud) 我正在编写一个 WinForm 组件,在那里我启动一个任务来进行实际处理并在继续时捕获异常。从那里我想在 UI 元素上显示异常消息。
Task myTask = Task.Factory.StartNew (() => SomeMethod(someArgs));
myTask.ContinueWith (antecedant => uiTextBox.Text = antecedant.Exception.Message,
TaskContinuationOptions.OnlyOnFaulted);
Run Code Online (Sandbox Code Playgroud)
现在我收到一个跨线程异常,因为该任务正在尝试从一个明显的非 UI 线程更新 UI 元素。
但是,在 Component 类中没有定义 Invoke 或 BeginInvoke。
如何从这里开始?
更新
另外,请注意 Invoke/BeginInvoke/InvokeRequired 在我的 Component 派生类中不可用,因为 Component 不提供它们。
当我加载窗体时,使用新线程,我每秒向列表框添加一个随机数,当它达到10个数字时,我生成一组10个随机数.但是,目前,我遇到了UI线程的问题.随机数被添加到列表框中,但我无法控制表单.当我尝试与表单进行交互时,UI会冻结.我是否错误地使用了MethodInvoker.任何意见,将不胜感激.
public Form1()
{
InitializeComponent();
Thread ranThread = new Thread(new ThreadStart(RandomList));
ranThread.IsBackground = true;
ranThread.Start();
}
public void RandomList()
{
stack = new Stack<int>();
while (loop)
{
if (lbxStackRndNum.InvokeRequired)
{
lbxStackRndNum.Invoke(new MethodInvoker(delegate
{
Random rnd = new Random();
if (lbxStackRndNum.Items.Count == 10)
{
stack.Clear();
lbxStackRndNum.Items.Clear();
}
int rndVal = rnd.Next(1, 10000);
stack.Push(rndVal);
lbxStackRndNum.Items.Insert(0, rndVal);
Thread.Sleep(1000);
}));
}
}
}
Run Code Online (Sandbox Code Playgroud) 我正在使用第三方工具,在该工具中我收到了 InvalidOperationException(实际上,这最终发生在 PresentationFramework.dll 中):
调用线程无法访问此对象,因为其他线程拥有它。
我尝试了使用 Invoke 的任何变体,包括 BeginInvoke,但没有任何变化。
会话 session = new ThirdPartyTool.Session();
Application.Current.Dispatcher.Invoke(DispatcherPriority.Normal, (Action)(() => session.Open(view)));
使用 Google 时,我只找到建议使用 Invoke 的“解决方案”。好吧,我确实使用 Invoke。
其他问题及其在 stackoverflow 上的相应答案也无济于事。
我还能做些什么来追查真正的原因?
编辑:我再次查看了线程窗口,完整的调用堆栈位于主线程中。AFAIK,这表明调用是多余的。
Edit2:
在调用 open 时不会直接引发错误。ThirdPartyTool 初始化一个列表框,当测量这个列表框时,表示框架中发生错误:

实际异常被包装到 XamlParseException 中。完整的异常细节:
System.Windows.Markup.XamlParseException occurred
HResult=-2146233087
Message=The calling thread cannot access this object because a different thread owns it.
Source=PresentationFramework
LineNumber=0
LinePosition=0
StackTrace:
at System.Windows.FrameworkTemplate.LoadTemplateXaml(XamlReader templateReader, XamlObjectWriter currentWriter)
InnerException: System.InvalidOperationException
HResult=-2146233079
Message=The calling thread cannot access this object because a different thread owns it.
Source=WindowsBase
StackTrace: …Run Code Online (Sandbox Code Playgroud) 我需要运行一个Powershell脚本,其中包含以下语法.这条线的PowerShell 2相当于什么?
Invoke-WebRequest "http://$Server/api/setobjectproperty.htm?id=$Id&name=Inheritscheduledependency&value=0&username=$User&passhash=$Hash" | out-null
Run Code Online (Sandbox Code Playgroud)
这是完整的脚本:
param([int]$Id = 5557,[int]$Duration = 1,[string]$Unit = "Hours")
$Server = "webpage.bla.org"
$User = "user"
$Hash = "45093450908"
$DateFormat = "yyyy-MM-dd-HH-mm-ss";
$StartDate = (Get-Date).ToString($DateFormat);
switch($Unit){
"Minutes" { $EndDate = (Get-Date).AddMinutes($Duration).ToString($DateFormat); }
"Hours" { $EndDate = (Get-Date).AddHours($Duration).ToString($DateFormat); }
"Days" { $EndDate = (Get-Date).AddDays($Duration).ToString($DateFormat); }
default { $EndDate = (Get-Date).AddHours($Duration).ToString($DateFormat); }
}
Invoke-WebRequest "http://$Server/api/setobjectproperty.htm?id=$Id&name=Inheritscheduledependency&value=0&username=$User&passhash=$Hash" | out-null
Invoke-WebRequest "http://$Server/api/setobjectproperty.htm?id=$Id&name=maintenable&value=1&username=$User&passhash=$Hash" | out-null
Invoke-WebRequest "http://$Server/api/setobjectproperty.htm?id=$Id&name=maintstart&value=$StartDate&username=$User&passhash=$Hash" | out-null
Invoke-WebRequest "http://$Server/api/setobjectproperty.htm?id=$Id&name=maintend&value=$EndDate&username=$User&passhash=$Hash" | out-null
Run Code Online (Sandbox Code Playgroud)
谢谢
我有一个关于 invoke 用法的一般问题。我的大多数 C# winforms 项目都有一个后台工作人员和一个 UI。很快我意识到我需要来自后台工作人员 UI 的信息,或者我需要更改我的后台工作人员的 UI。例子:
//example invoke usage to get information from UI (dateMatch = CheckBox, fromDate&toDate = Datepicker)
bool isDateMatch = false;
dateMatch.Invoke(new MethodInvoker(delegate { isDateMatch = dateMatch.Checked; }));
DateTime fromDt = new DateTime();
fromDate.Invoke(new MethodInvoker(delegate { fromDt = fromDate.Value; }));
DateTime toDt = new DateTime();
toDate.Invoke(new MethodInvoker(delegate { toDt = toDate.Value; }));
Run Code Online (Sandbox Code Playgroud)
//example invoke usage to change UI (statusTxt = TextBox, progressBar = ProgressBar)
private void changeStatus(string statusTextV, bool enableProgressBar)
{
statusTxt.Invoke(new MethodInvoker(delegate …Run Code Online (Sandbox Code Playgroud) 我想从另一个线程中的FTP服务器下载文件.问题是,这个线程导致我的应用程序被冻结.在这里你有代码,我做错了什么?任何帮助都会感激不尽:)
(当然我想停止循环,直到线程'ReadBytesThread'终止.)我创建一个新线程:
DownloadThread = new Thread(new ThreadStart(DownloadFiles));
DownloadThread.Start();
private void DownloadFiles()
{
if (DownloadListView.InvokeRequired)
{
MyDownloadDeleg = new DownloadDelegate(Download);
DownloadListView.Invoke(MyDownloadDeleg);
}
}
private void Download()
{
foreach (DownloadingFile df in DownloadingFileList)
{
if (df.Size != "<DIR>") //don't download a directory
{
ReadBytesThread = new Thread(() => {
FileData = sendPassiveFTPcmd("RETR " + df.Path + "/" + df.Name + "\r\n");
FileStream fs = new FileStream(@"C:\Downloads\" + df.Name, FileMode.Append);
fs.Write(FileData, 0, FileData.Length);
fs.Close();
});
ReadBytesThread.Start();
(here->) ReadBytesThread.Join();
MessageBox.Show("Downloaded");
}
}
}
Run Code Online (Sandbox Code Playgroud) 你在跟我开玩笑!在发布此问题后几秒钟,我决定以不同的方式搜索,并以某种方式遇到以下内容:[DllImport("kernel32.dll",SetLastError = true,CharSet = CharSet.Unicode)] private static extern Microsoft.Win32.SafeHandles .SafeFileHandle CreateFile(string lpFileName,System.UInt32 dwDesiredAccess,System.UInt32 dwShareMode,IntPtr pSecurityAttributes,System.UInt32 dwCreationDisposition,System.UInt32 dwFlagsAndAttributes,IntPtr hTemplateFile); 欢迎大家编写代码 - 对于由此造成的任何不便,我深感抱歉.
我目前遇到了最奇怪的问题 - 我发现这个问题没有得到很好的记录.我试图通过C#.net使用各种API,如CreateFile,ReadFile等.我在使用MessageBox API时取得了一些成功,但在尝试使用CreateFile时遇到错误.我将在下面详细解释.
Step 1: Declarations
a) MessageBox Declaration
1) VB6:`// Public Declare Function MessageBox Lib "user32" Alias "MessageBoxA" (ByVal hwnd As Long, ByVal lpText As String, ByVal lpCaption As String, ByVal wType As Long) As Long`
2) C#: `public static extern int MessageBox(int hwnd, string lptxt, string lcap, int wType);`
Step 2: C# Usage: `MessageBox(0, "Text", "Caption", … 可能重复:
在进入主函数之前,你能用C++打印任何东西吗?
在调用int main()之前是否有可能运行任何其他指令?
int main(){cout<<"a";}
Run Code Online (Sandbox Code Playgroud)
在调用main()之前,调用cout <<"b"; 以前的某个地方.也许这个#define的东西可以提供帮助.
从另一个线程更新UI这两种方法中哪一种更好?(对我来说,他们都工作,但哪个更安全?)我更喜欢SetPropertyThreadSafe方法,因为它需要更少的代码.
1.
label1.SetPropertyThreadSafe(() => this.label1.Text, "New Value");
Run Code Online (Sandbox Code Playgroud)
2.
if (label1.InvokeRequired)
{
label1.Invoke(new MethodInvoker(delegate {
label1.Text="New Value"; }));
}
Run Code Online (Sandbox Code Playgroud)