如何在Windows-API-Code-Pack中修复ArgumentException?

问题描述 投票:1回答:2

我创建了一个应用程序,它使用this包中的Windows-API-Code-Pack从文件中读取属性。我在检索属性时遇到问题

var width = fileInfo.Properties.GetProperty(SystemProperties.System.Video.FrameWidth).ValueAsObject;

这里的代码打破了我

System.ArgumentException: An item with the same key has already been added.
   at System.ThrowHelper.ThrowArgumentException(ExceptionResource resource)
   at System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add)
   at Microsoft.WindowsAPICodePack.Shell.PropertySystem.ShellPropertyFactory.GenericCreateShellProperty[T](PropertyKey propKey, T thirdArg)
   at Microsoft.WindowsAPICodePack.Shell.PropertySystem.ShellProperties.GetProperty(PropertyKey key)

这主要发生在PLINQ中调用此部分代码时

.AsParallel().WithDegreeOfParallelism(_maxConcurrentThreads).ForAll(...)

即使学位设置为1.我该如何解决?

c# shell plinq windows-api-code-pack
2个回答
1
投票

要扩展现有答案,将Dictionary转换为ConcurrentDictionary也可以解决问题并消除对锁的需求。

    private static ConcurrentDictionary<int, Func<PropertyKey, ShellPropertyDescription, object, IShellProperty>> _storeCache
        = new ConcurrentDictionary<int, Func<PropertyKey, ShellPropertyDescription, object, IShellProperty>>();
...

    private static IShellProperty GenericCreateShellProperty<T>(PropertyKey propKey, T thirdArg)
    {
       ...

        Func<PropertyKey, ShellPropertyDescription, object, IShellProperty> ctor;
        ctor = _storeCache.GetOrAdd((hash, (key, args) -> {
            Type[] argTypes = { typeof(PropertyKey), typeof(ShellPropertyDescription), args.thirdType };
            return ExpressConstructor(args.type, argTypes);
        }, {thirdType, type});

        return ctor(propKey, propDesc, thirdArg);
    }

0
投票

根据stuartd的建议,我能够通过修改包的源代码并在第57和62行的this code中添加锁来解决这个问题,就像这样

lock (_storeCache)
{
    if (!_storeCache.TryGetValue(hash, out ctor))
    {
        Type[] argTypes = { typeof(PropertyKey), typeof(ShellPropertyDescription), thirdType };
        ctor = ExpressConstructor(type, argTypes);
        lock (_storeCache)
            _storeCache.Add(hash, ctor);
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.