有没有在C#中列出℃的方法; T>像C ++的调整矢量< T>
当我使用调整(INT newsize)
在C ++中的矢量< T>
,这意味着尺寸这个矢量>
设置为 newsize
和指标运行在范围 [0..newsize)
。如何做到在C#中同为列表< T>
结果
更改列表< T>
属性容量
只改变了容量
,但离开计数
相同,此外指标仍然在范围内的 [0..Count)
。帮助我,请。
When I use resize(int newsize)
in C++ for vector<T>
, it means that the size
of this vector
are set to newsize
and the indexes run in range [0..newsize)
. How to do the same in C# for List<T>
?
Changing the List<T>
property Capacity
only changes the Capacity
but leaves the Count
the same, and furthermore the indexes still are in range [0..Count)
. Help me out, please.
P.S。想象一下,我有一个矢量< T> TMP
与 tmp.size()== 5
我不能引用 TMP [9]
,但是当我再使用 tmp.resize(10)
我可参照 TMP [9]
。在C#中,如果我有列表< T> TMP
与 tmp.Count == 5
我不能引用 TMP [9]
( IndexOutOfRangeException
),但即使当我设置 tmp.Capacity = 10
我将无法引用 TMP [9]
堂妹的 tmp.Count
还是5.我想找到大小调整的一些比喻在C#。
P.S. Imagine I have a vector<T> tmp
with a tmp.size() == 5
I cannot refer to tmp[9]
, but when I then use tmp.resize(10)
I may refer to tmp[9]
. In C# if I have List<T> tmp
with tmp.Count == 5
I cannot refer to tmp[9]
(IndexOutOfRangeException
), but even when I set tmp.Capacity=10
I will not be able to refer to tmp[9]
coz of tmp.Count
is still 5. I want to find some analogy of resize in C#.
没有,但你可以使用扩展方法来添加自己的。以下具有相同的行为为的std ::矢量< T> ::调整()
,其中包括同时复杂性。唯一的区别是,在C ++中,我们可以定义无效调整大小默认(SIZE_TYPE SZ,T C = T())
和方式的模板工作意味着那很好,如果我们叫它不默认为 T
有没有可访问的参数的构造函数。在C#中,我们不能做到这一点,所以不是我们要创建一个方法,没有约束的非默认使用的情况下匹配,另一个与,其中新()
约束在调用它
No, but you can use extension methods to add your own. The following has the same behaviour as std::vector<T>::resize()
, including the same time-complexity. The only difference is that in C++ we can define a default with void resize ( size_type sz, T c = T() )
and the way templates work means that that's fine if we call it without the default for a T
that has no accessible parameterless constructor. In C# we can't do that, so instead we have to create one method with no constraint that matches the non-default-used case, and another with a where new()
constraint that calls into it.
public static class ListExtra
{
public static void Resize<T>(this List<T> list, int sz, T c)
{
int cur = list.Count;
if(sz < cur)
list.RemoveRange(sz, cur - sz);
else if(sz > cur)
{
if(sz > list.Capacity)//this bit is purely an optimisation, to avoid multiple automatic capacity changes.
list.Capacity = sz;
list.AddRange(Enumerable.Repeat(c, sz - cur));
}
}
public static void Resize<T>(this List<T> list, int sz) where T : new()
{
Resize(list, sz, new T());
}
}
现在 myList中的喜欢.Resize(23)
或 myList.Resize(23 myDefaultValue)
将匹配什么人从C ++的矢量的期望。我注意到,虽然有时在那里与C ++,你就会有指针的载体,在C#中你有一定的参考类型的列表。因此,在所在的C ++ T()
产生一个空指针(因为它是一个指针)的情况下,我们在这里期待它来调用参数的构造函数。出于这个原因,你可能会发现它更接近你习惯的行为,以取代与第二种方法:
Now the likes of myList.Resize(23)
or myList.Resize(23, myDefaultValue)
will match what one expects from C++'s vector. I'd note though that sometimes where with C++ you'd have a vector of pointers, in C# you'd have a list of some reference-type. Hence in cases where the C++ T()
produces a null pointer (because it's a pointer), here we're expecting it to call a parameterless constructor. For that reason you might find it closer to the behaviour you're used to to replace the second method with:
public static void Resize<T>(this List<T> list, int sz)
{
Resize(list, sz, default(T));
}
这与值类型(调用参数的构造函数),但具有相同的效果引用类型,它就会用null填充。在这种情况下,我们就可以重写整个类:
This has the same effect with value types (call parameterless constructor), but with reference-types, it'll fill with nulls. In which case, we can just rewrite the entire class to:
public static class ListExtra
{
public static void Resize<T>(this List<T> list, int sz, T c = default(T))
{
int cur = list.Count;
if(sz < cur)
list.RemoveRange(sz, cur - sz);
else if(sz > cur)
list.AddRange(Enumerable.Repeat(c, sz - cur));
}
}
请注意,这是不是这么多的差异的std ::矢量< T>
和列表< T>
约在指针是如何在C中使用的差异++和C#。
Note that this isn't so much about differences between std::vector<T>
and List<T>
as about the differences in how pointers are used in C++ and C#.