如何将字典转换为ConcurrentDictionary?

时间:2021-06-17 13:13:11

I have seen how to convert a ConcurrentDictionary to a Dictionary, but I have a dictionary and would like to convert to a ConcurrentDictionary. How do I do that?... better yet, can i set the link statement to be a ConcurrentDictionary?

我已经看到如何将ConcurrentDictionary转换为Dictionary,但我有一个字典,并希望转换为ConcurrentDictionary。我该怎么做?...更好的是,我可以将link语句设置为ConcurrentDictionary吗?

var customers = _customerRepo.Query().Select().ToDictionary(x => x.id, x => x);

4 个解决方案

#1


16  

Use ConcurrentDictionary<TKey, TValue> Constructor (IEnumerable<KeyValuePair<TKey, TValue>>) constructor which can accept a dictionary object like:

使用ConcurrentDictionary 构造函数(IEnumerable >)构造函数,它可以接受如下的字典对象: ,tvalue>

Dictionary<int, string> dictionary = new Dictionary<int, string>();
dictionary.Add(1,"A");
dictionary.Add(2, "B");

ConcurrentDictionary<int,string> concurrentDictionary = 
             new ConcurrentDictionary<int, string>(dictionary);

can i set the LINQ statement to be a ConcurrentDictionary?

我可以将LINQ语句设置为ConcurrentDictionary吗?

No. You can not. . There is no extension method available to create ConcurrentDictionary in LINQ. You can either create your own extension method or you can use the ConcurrentDictionary constructor in your LINQ query while projecting results.

你不能。 。在LINQ中没有可用于创建ConcurrentDictionary的扩展方法。您可以创建自己的扩展方法,也可以在投影结果时在LINQ查询中使用ConcurrentDictionary构造函数。

#2


4  

Why not write your own extension method:

为什么不编写自己的扩展方法:

  public static class ConcurrentDictionaryExtensions {
    public static ConcurrentDictionary<TKey, TElement> ToConcurrentDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector, IEqualityComparer<TKey> comparer) {
        if (source == null) throw new ArgumentNullException("source");
        if (keySelector == null) throw new ArgumentNullException("keySelector");
        if (elementSelector == null) throw new ArgumentNullException("elementSelector");

        ConcurrentDictionary<TKey, TElement> d = new ConcurrentDictionary<TKey, TElement>(comparer);
        foreach (TSource element in source)
            d.TryAdd(keySelector(element), elementSelector(element));

        return d;
    }

    public static ConcurrentDictionary<TKey, TSource> ToConcurrentDictionary<TSource, TKey>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector) {
        return ToConcurrentDictionary<TSource, TKey, TSource>(source, keySelector, IdentityFunction<TSource>.Instance, null);
    }

    public static ConcurrentDictionary<TKey, TSource> ToConcurrentDictionary<TSource, TKey>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, IEqualityComparer<TKey> comparer) {
        return ToConcurrentDictionary<TSource, TKey, TSource>(source, keySelector, IdentityFunction<TSource>.Instance, comparer);
    }

    public static ConcurrentDictionary<TKey, TElement> ToConcurrentDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector) {
        return ToConcurrentDictionary<TSource, TKey, TElement>(source, keySelector, elementSelector, null);
    }

    internal class IdentityFunction<TElement> {
        public static Func<TElement, TElement> Instance
        {
            get { return x => x; }
        }
    }

}

Simply adopted the code from the .Net framework.

简单地采用了.Net框架中的代码。

#3


2  

A LINQ-To-Objects statement is ultimately an IEnumerable so you can pass it to the ConcurrentDictionary constructor, eg:

LINQ-To-Objects语句最终是一个IEnumerable,因此您可以将它传递给ConcurrentDictionary构造函数,例如:

var customers = myCustomers.Select(x => new KeyValuePair(x.id, x));
var dictionary=new ConcurrentDictionary(customers);

This may not work with other providers. Linq to Entities for example, converts the entire LINQ statement to SQL and can't projection to a KeyValuePair. In this case you may have to call AsEnumerable() or any other method that forces the IQueryable to execute, eg:

这可能不适用于其他提供商。例如,Linq to Entities将整个LINQ语句转换为SQL,无法投影到KeyValuePair。在这种情况下,您可能必须调用AsEnumerable()或强制IQueryable执行的任何其他方法,例如:

var customers = _customerRepo.Customers.Where(...)
                             .AsEnumerable()
                             .Select(x => new KeyValuePair(x.id, x));
var dictionary=new ConcurrentDictionary(customers);

Select() with no arguments is not an IEnumerable or IQueryable method so I suppose it's a method provided by some other ORM. If Select() returns an IEnumerable you can use the first option, otherwise you can use AsEnumerable()

没有参数的Select()不是IEnumerable或IQueryable方法,所以我想这是一个其他ORM提供的方法。如果Select()返回IEnumerable,则可以使用第一个选项,否则可以使用AsEnumerable()

#4


0  

Or just a have method:

或者只是一个有方法:

 private ConcurrentDictionary<TKey, TValue> ToConcurrent<TKey, TValue>(Dictionary<TKey, TValue> dic) {
        return new ConcurrentDictionary<TKey, TValue>(dic);
    }

and then do:

然后做:

var customers = _customerRepo.Query().Select().ToDictionary(x => x.id, x => x);
var concurrentDic = ToConcurrent(customers);

Personally, I'm going with the extension method that I just updated...

就个人而言,我正在使用我刚刚更新的扩展方法...

#1


16  

Use ConcurrentDictionary<TKey, TValue> Constructor (IEnumerable<KeyValuePair<TKey, TValue>>) constructor which can accept a dictionary object like:

使用ConcurrentDictionary 构造函数(IEnumerable >)构造函数,它可以接受如下的字典对象: ,tvalue>

Dictionary<int, string> dictionary = new Dictionary<int, string>();
dictionary.Add(1,"A");
dictionary.Add(2, "B");

ConcurrentDictionary<int,string> concurrentDictionary = 
             new ConcurrentDictionary<int, string>(dictionary);

can i set the LINQ statement to be a ConcurrentDictionary?

我可以将LINQ语句设置为ConcurrentDictionary吗?

No. You can not. . There is no extension method available to create ConcurrentDictionary in LINQ. You can either create your own extension method or you can use the ConcurrentDictionary constructor in your LINQ query while projecting results.

你不能。 。在LINQ中没有可用于创建ConcurrentDictionary的扩展方法。您可以创建自己的扩展方法,也可以在投影结果时在LINQ查询中使用ConcurrentDictionary构造函数。

#2


4  

Why not write your own extension method:

为什么不编写自己的扩展方法:

  public static class ConcurrentDictionaryExtensions {
    public static ConcurrentDictionary<TKey, TElement> ToConcurrentDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector, IEqualityComparer<TKey> comparer) {
        if (source == null) throw new ArgumentNullException("source");
        if (keySelector == null) throw new ArgumentNullException("keySelector");
        if (elementSelector == null) throw new ArgumentNullException("elementSelector");

        ConcurrentDictionary<TKey, TElement> d = new ConcurrentDictionary<TKey, TElement>(comparer);
        foreach (TSource element in source)
            d.TryAdd(keySelector(element), elementSelector(element));

        return d;
    }

    public static ConcurrentDictionary<TKey, TSource> ToConcurrentDictionary<TSource, TKey>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector) {
        return ToConcurrentDictionary<TSource, TKey, TSource>(source, keySelector, IdentityFunction<TSource>.Instance, null);
    }

    public static ConcurrentDictionary<TKey, TSource> ToConcurrentDictionary<TSource, TKey>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, IEqualityComparer<TKey> comparer) {
        return ToConcurrentDictionary<TSource, TKey, TSource>(source, keySelector, IdentityFunction<TSource>.Instance, comparer);
    }

    public static ConcurrentDictionary<TKey, TElement> ToConcurrentDictionary<TSource, TKey, TElement>(this IEnumerable<TSource> source, Func<TSource, TKey> keySelector, Func<TSource, TElement> elementSelector) {
        return ToConcurrentDictionary<TSource, TKey, TElement>(source, keySelector, elementSelector, null);
    }

    internal class IdentityFunction<TElement> {
        public static Func<TElement, TElement> Instance
        {
            get { return x => x; }
        }
    }

}

Simply adopted the code from the .Net framework.

简单地采用了.Net框架中的代码。

#3


2  

A LINQ-To-Objects statement is ultimately an IEnumerable so you can pass it to the ConcurrentDictionary constructor, eg:

LINQ-To-Objects语句最终是一个IEnumerable,因此您可以将它传递给ConcurrentDictionary构造函数,例如:

var customers = myCustomers.Select(x => new KeyValuePair(x.id, x));
var dictionary=new ConcurrentDictionary(customers);

This may not work with other providers. Linq to Entities for example, converts the entire LINQ statement to SQL and can't projection to a KeyValuePair. In this case you may have to call AsEnumerable() or any other method that forces the IQueryable to execute, eg:

这可能不适用于其他提供商。例如,Linq to Entities将整个LINQ语句转换为SQL,无法投影到KeyValuePair。在这种情况下,您可能必须调用AsEnumerable()或强制IQueryable执行的任何其他方法,例如:

var customers = _customerRepo.Customers.Where(...)
                             .AsEnumerable()
                             .Select(x => new KeyValuePair(x.id, x));
var dictionary=new ConcurrentDictionary(customers);

Select() with no arguments is not an IEnumerable or IQueryable method so I suppose it's a method provided by some other ORM. If Select() returns an IEnumerable you can use the first option, otherwise you can use AsEnumerable()

没有参数的Select()不是IEnumerable或IQueryable方法,所以我想这是一个其他ORM提供的方法。如果Select()返回IEnumerable,则可以使用第一个选项,否则可以使用AsEnumerable()

#4


0  

Or just a have method:

或者只是一个有方法:

 private ConcurrentDictionary<TKey, TValue> ToConcurrent<TKey, TValue>(Dictionary<TKey, TValue> dic) {
        return new ConcurrentDictionary<TKey, TValue>(dic);
    }

and then do:

然后做:

var customers = _customerRepo.Query().Select().ToDictionary(x => x.id, x => x);
var concurrentDic = ToConcurrent(customers);

Personally, I'm going with the extension method that I just updated...

就个人而言,我正在使用我刚刚更新的扩展方法...