How can I access an element by index of a member List via a property? For example:
public class foo{
private List<type> list = new List<type>;
public List{
get{/*basically, what goes here?*/}
}
}
//Much later....
foo Foo = new foo();
Console.WriteLine(Foo.List[1]);
One thing to consider is what ability you want to provide to update the list. If you just expose the list as a get-only property, then there's nothing stopping someone from modifying the list:
public class foo{
private List<type> list = new List<type>;
public List<type> List{
get{return list}
}
}
//Much later....
foo Foo = new foo();
Foo.List.Clear(); // perfectly legal
If, however, you want a "read-only" list exposed, then you can expose the list as read-only:
public class foo{
private List<type> list = new List<type>;
public IList<type> List{
get{return list.AsReadOnly()}
}
}
//Much later....
foo Foo = new foo();
Foo.List.Clear(); // not possible
EDIT
Based on your comment to another question, it is unclear whether you want to expose the list as a property or access items by index. For the latter you can add an indexer to the class:
public class foo{
private List<type> list = new List<type>;
public type this[int i]{
get{return list[i]}
get{list[i] = value}
}
}
//Much later....
foo Foo = new foo();
Console.WriteLine(Foo[1]);
Since you already have a list, you can just return that list in the property
public class foo{
private List<type> list = new List<type>;
public List<type> List{
get{ return list; }
}
}
Related
I have a class A that contains a List field.
public class A
{
public List<int> list = new List<int>();
}
I would like to remove an element from the list from class B without making the list in class A static. How can I do that?
You could create an instance of class A inside a method in class B. Then you could access the list field, like this:
public class B
{
void method()
{
A a = new A();
int item = 2;
a.list.Remove(item);
}
}
A more OOP solution for this problem would be:
public class A
{
private List<int> list = new List<int>();
List<int> getList();
void setList(List<int> list);
}
Then in the code where it is used,
A a = new A();
List<int> list = a.getList();
modify list as you want
a.setList(list);
If you don't mind instantiating it, it's simply
A a = new A();
a.list...
If you don't want to instantiate a new one, you can pass an existing instance to B on its constructor:
public class B{
private A myA;
public B( A a) {
this.myA = a;
}
public doSomething(){
this.myA....
}
}
Now you can use A as a field of B.
Ok, so here's the basic code:
class foo
{
String name;
int property;
}
class bar
{
private List<foo> a;
private List<foo> b;
}
I'd like to make it so that calling code can iterate over either list but I want to keep them protected from editing. I've looked into implementing the IEnumarable interface but the problem is that it expects a single "GetEnumerable" definition, but I want two different enumerators. For instance, i want to be able to say
foreach(foo in bar.getA())
{ //do stuff }
and then
foreach(foo in bar.getB())
{ //do stuff }
Do I have to subclass each element and implement the IEnumerable interface over each, and then include THOSE as properties? Am I misunderstanding the IEnumerable interface? I know that the List class has it's own Enumerator, so I could do something like
class bar
{
private List<foo> a;
private List<foo> b;
public IEnumerator<foo> getAEnumerator()
{ return a.GetEnumerator();
public IEnumerator<foo> getBEnumerator()
{ return b.GetEnumerator();
}
but then my for loops look like this:
bar x = new bar();
IEnumerator<foo> y = x.getAEnumerator();
while (y.moveNext())
{
foo z = y.Current;
}
so I lose the readability of "foreach".
Is there a way to accomplish using "foreach" over these lists without exposing these lists publicly? I'm still trying to get my head around the IENumerable interface, so maybe I'm missing something obvious.
Don't expose a List<T>, expose something else, like an IReadOnlyList<T> instead:
class bar
{
private readonly List<foo> a = new List<foo>();
private readonly List<foo> b = new List<foo>();
public IReadOnlyList<foo> A { get; private set; }
public IReadOnlyList<foo> B { get; private set; }
public bar()
{
A = a.AsReadOnly();
B = b.AsReadOnly();
}
}
Any changes to a and b will reflect in A and B.
Also note that while you can cast a List<T> to an IReadOnlyList<T>, the calling code can cast it back to List<T>. The above method returns a ReadOnlyCollection<T> which provides a safeguard against casting back to a mutable collection type.
The readonly keyword only ensures you don't substitute references to a and b with something else later on.
class bar
{
private readonly List<foo> a = new List<foo>();
private readonly List<foo> b = new List<foo>();
public IReadOnlyList<foo> A { get {return a.AsReadOnly();}}
public IReadOnlyList<foo> B { get {return b.AsReadOnly();}}
}
this way you'll not even have to initialize it, and no need to any kind of set
Here is what I am trying to do. I am making a class which contains indexer for accessing fields within the class, and for adding/removing new fields. Basically the class is like a class with set of static and dynamic fields. I am using a dictionary for the indexer. My problem is that how would I find out and update the static object in the dictionary when the user explicitly reinitialized one of the field? example:
public class foo
{
}
public class bar
{
Dictionary<string, foo> dict = new Dictionary<string, foo>();
public bar()
{
//using reflection to initialize all fields
}
public foo this[string name]
{
get
{
return dict[name];
}
}
}
public class bar2:bar //Note: defined by the user, can't use get/setter to update it
{
public foo field1;
public foo field2;
public foo field3;
}
public static void main()
{
bar2 test = new bar2();
test.field1 = new foo();
test["field1"] //this points to the old field1. How can I update it automatically when test.field1 = new foo(); is called?
}
Some of you might suggest me to use reflection to do it, but what if the user called remove "field1" and added a new dynamic field called field1, I would want to return the new one created by the user instead of the one defined in the class.
If your users and defining fields then you will need to adjust your logic to dynamically look up the result every time. Luckily you can avoid most of the reflection overhead by storing the field in your dictionary.
Dictionary<string, FieldInfo> dict = new Dictionary<string, FieldInfo>();
public bar()
{
//If you are using reflection you should be getting this
FieldInfo info;
dict[info.Name] = info;
}
public foo this[string name]
{
get { return dict[name].GetValue(this); }
set { dict[name].SetValue(this, value); }
}
I have two classes:
public class Foo<T>{}
public class Bar
{
private List<Foo> foos = new List<Foo>();
public Foo GetFoo(int index)
{
return foos[index];
}
}
However, both the list and method say that i need a type parameter for the Foos i specify, but i just want Foos in general, so i could add a Foo< int >, a Foo< float >, a Foo< Baz > etc. etc. to the list, and then have the method return a Foo with an unknown type. And making GetFoo generic is OK if it helps, but I can't figure out how it would.
You could make Foo<T> derive from a base class (or implement an interface) that is non-generic. You could then return a List<IFoo> with the properties that aren't specific to the type T.
This would allow you to have a single list containing any type of Foo<T>.
public abstract class Foo
{
//general foo logic here
}
public class Foo<T>: Foo
{
//generic type specific information here
}
public class Bar
{
private List<Foo> foos = new List<Foo>();
public Foo GetFoo(int index)
{
return foos[index];
}
}
Considering the following case in C#:
class Foo
{
public Foo() { }
}
class Foo2
{
private List<Foo> m_List = new List<Foo>();
public Foo2() { m_List.Add(new Foo); }
}
Foo2 fooInstance = new Foo2();
Foo2 owns a List that contains a Foo - is there any built-in way for the Foo to figure out which List it's contained in, and which object that list belongs to? In other words, can Foo obtain a reference to Foo2, or do I have to add an explicit backwards reference in Foo - pointing to Foo2 - as I've been doing?
No, there's no built-in way. Instances of Foo only know about themselves, the public interface of their members, and the public/protected interface of their base class, if they have one.
If you give a little more context about what you're trying to do, I may be able to offer you an alternative solution.
Foo will have no knowledge that it is contained within a list unless you specify that somehow. A list after all is just a set of references to a location in memory. There is no relationship from a pointer to what contains the pointer.
class Foo
{
public Foo2 Parent { get; protected set; }
public Foo(Foo2 parent)
{
Parent = parent;
}
}
class Foo2
{
public Foo2()
{
List<Foo> x = new List<Foo>
{
new Foo(this)
};
}
}
No; that's inherently impossible.
What if you put the same object in two lists?