我有一个代码允许用户选择一个文件,将一些关于它的信息添加到一个可观察的集合并显示上传进度,完成后,它将图像绑定(bind)到 ImageView 。它立即正常工作,但如果您重复该过程,则会抛出异常:
System.ArgumentOutOfRangeException: Index was out of range. Must be non-negative and less than the size of the collection.
Parameter name: index
at at (wrapper dynamic-method) Android.Runtime.DynamicMethodNameCounter.43(intptr,intptr)
at at (wrapper native-to-managed) Android.Runtime.DynamicMethodNameCounter.43(intptr,intptr)
插入新元素并获取其索引的代码
switch(x){
// some code...
case 6:
// .... some code
_ = Task.Run(async () => {
try
{
int i = default;
Msg newmsg2 = new Msg() { UploadProgress = 0.0, UploadProgressVisibility = true, IsImageSend = true, ImageSend = "@drawable/icon_default" };
valuesLock.EnterWriteLock();
try
{
// THE ISSUE IS RELATED WITH THIS WORK
Device.BeginInvokeOnMainThread(() => ListaMsg.Add(newmsg2));
}
finally
{
valuesLock.ExitWriteLock();
valuesLock.EnterReadLock();
try
{
// THE ISSUE IS RELATED WITH THIS WORK
i = ListaMsg.IndexOf(newmsg2);
// Some data can be added while the progress is being updated, I need to get the index of this exactly Item, can't get it with Count-1
}
finally
{
valuesLock.ExitReadLock();
Resultado a = await Task.Run(()=>UploadFile(filename, i));
if (a.status == "ok")
{
valuesLock.EnterWriteLock();
try
{
Device.BeginInvokeOnMainThread(() =>
{
MyList[i].msg = "Image was sent";
MyList[i].status = true;
MyList[i].ImageSend = "mydomain/assets/libs/thumb.php?h=150&w=150&img=" + a.msg;
});
}
finally
{
valuesLock.ExitWriteLock();
SendMsg(6, a.msg, i);
}
}
else
{
valuesLock.EnterWriteLock();
try
{
Device.BeginInvokeOnMainThread(() =>
{
MyList[i].ImageSend = "@drawable/icon_default";
MyList[i].icon = "\uf057";
MyList[i].IconColor = Xamarin.Forms.Color.Red;
});
}
finally { valuesLock.ExitWriteLock(); }
}
}
}
}
catch (Exception e)
{
...
}
});
break;
}
上传方法
public async Task<Resultado> UploadFile(string url, string filepath)
{
//some code
webclient.UploadProgressChanged += new UploadProgressChangedEventHandler(UploadProgressCallback);
//some code
}
最后是 ProgressChanged 回调:
private void UploadProgressCallback(object sender, UploadProgressChangedEventArgs e, int idreference)
{
double temp = ((double)e.BytesSent) / filesize;
Device.BeginInvokeOnMainThread(() => {
valuesLock.EnterWriteLock();
try
{
// THE EXCEPTION IS BEING THREW AT LINE BELOW, idreference value is -1 and not the correct index
MyList[idreference].UploadProgress = temp;
}
finally { valuesLock.ExitWriteLock(); }
});
}
为什么这只一次有效?是我漏掉了还是做错了什么?
最佳答案
问题的根源在于包含 IndexOf() 方法的部分。它在主线程上执行之前执行,索引始终为 -1。通过更改修复:
Device.BeginInvokeOnMainThread(() => ... );
通过
await Device.InvokeOnMainThreadAsync(() => { ... } );
关于c# - 向 ObservableCollection 添加元素会导致异常 Index was out of range,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61554098/