简体   繁体   English

C#foreach错误

[英]C# foreach error

string connection = "Data Source=" + server + ";Initial Catalog=" + dbase + 
";User ID=" + userid + ";Password=" + password;

conn = new SqlConnection(connection);
conn.Open();
SqlCommand cmd = new SqlCommand("SUBNETTEMP", conn);
cmd.CommandType = CommandType.StoredProcedure;

Parameters d = new Parameters();
d.addparam(15, 1);
d.addparam(15, 2);

foreach (var param in d)
{
    cmd.Parameters.Add(new SqlParameter(param.Key, param.Value));
} 

There's a class called parameters: 有一个称为参数的类:

class Parameters
{
    Dictionary<int, int> paramids;
    public Dictionary<int, int> addparam(int sid, int sbid)
    {
        if (paramids == null)
            paramids = new Dictionary<int, int>();
        paramids.Add(sid, sbid);
        return paramids;
    }
}

I am not sure why I am getting error :"foreach statement cannot operate on variables of type 'ConsoleApplication1.Parameters' because 'ConsoleApplication1.Parameter' doesnot contain public definition for GetEnumerator. 我不确定为什么会收到错误消息:“ foreach语句无法对'ConsoleApplication1.Parameters'类型的变量进行操作,因为'ConsoleApplication1.Parameter'不包含GetEnumerator的公共定义。

Your Parameters class has no GetEnumerator method. 您的Parameters类没有GetEnumerator方法。 Just like the error said. 就像错误说的那样。

You can either iterate over the paramids field, but for that you'd need to publicly expose it, which is a bad idea IMO. 您可以遍历paramids字段,但是为此,您需要公开公开它,这对IMO是个坏主意。

The alternative is implementing GetEnumerator , forwarding it to paramids.GetEnumerator : 另一种方法是实现GetEnumerator ,将其转发到paramids.GetEnumerator

public IEnumerator<KeyValuePair<int,int>> GetEnumerator()
{
    return paramids.GetEnumerator();
}

For good measure you should also add and implement the IEnumerable<KeyValuePair<int,int>> and IEnumerable interfaces, even if they're not necessary for a simple foreach . 为了获得良好的效果,您还应该添加并实现IEnumerable<KeyValuePair<int,int>>IEnumerable接口,即使它们对于简单的foreach并不是必需的。


As a side-note: I consider exposing the internal dictionary as the return value of addparam a dubious design choice. 附带说明:我认为将内部字典公开为addparam的返回值是一种可疑的设计选择。 If you want a fluent API return your own instance of Parameters , and not the internal dictionary. 如果您希望使用流畅的API,请返回您自己的Parameters实例,而不是内部字典。 Ie use return this . 即使用return this

Also I'd use the .net naming conventions, so call your method AddParam not addparam . 另外,我会使用.net命名约定,因此请调用方法AddParam而不是addparam


So your complete class would be: 因此,您的完整课程将是:

class Parameters:IEnumerable<KeyValuePair<int,int>>
{
    Dictionary<int, int> paramids;

    public Parameters AddParam(int sid, int sbid)
    {
        if (paramids == null)
            paramids = new Dictionary<int, int>();
        paramids.Add(sid, sbid);
        return this;
    }

    public IEnumerator<KeyValuePair<int,int>> GetEnumerator()
    {
        return paramids.GetEnumerator();
    }

    System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
    {
        return GetEnumerator();
    }
}

Your Parameters class would need to either inherit from Dictionary , or expose its inner dictionary to enumerate via foreach : 您的Parameters类将需要从Dictionary继承,或公开其内部字典以通过foreach进行枚举:

class Parameters {
    Dictionary<int, int> paramids;
    ....
    public Dictionary<int, int> ParamIDs {
        get { return paramids; }
    }
}

So now this would work: 所以现在这可以工作:

foreach (var param in d.ParamIDs) {
....
}

Parameters does not have a GetEnumerator()? Parameters没有GetEnumerator()? method, which is what foreach relies on for looping over a collection. 方法, foreach在集合上循环所依赖。 You should refactor out the Parameters class (it looks a bit over-crafted to have a separate class for that) and use a Dictionary<> directly. 您应该重构Parameters类(为它提供了一个单独的类,看起来有些过高),并直接使用Dictionary<>

An alternative is to have Parameters implement GetEnumerator() : 一种替代方法是让Parameters实现GetEnumerator()

class Parameters
{
    Dictionary<int, int> paramids;
    public Dictionary<int, int> addparam(int sid, int sbid)
    {
        if (paramids == null)
            paramids = new Dictionary<int, int>();
        paramids.Add(sid, sbid);
        return paramids;
    }

    public IEnumerator<KeyValuePair<int, int>> GetEnumerator() 
    { 
        return paramids.GetEnumerator(); 
    }
}

If you want to use your Parameters class as dictionary - inherit it from Dictionary<int, int> : 如果要将Parameters类用作字典,请从Dictionary<int, int>继承它:

class Parameters: Dictionary<int, int>
{
}

but in this case maybe better to use just Dictionary<int, int> 但是在这种情况下,最好只使用Dictionary<int, int>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM