C# 增长列表和元素指针

发布于 2024-10-16 08:11:32 字数 502 浏览 4 评论 0原文

我需要一个不断增长的数组或列表(内置的就足够了)。此外,我需要能够使用指向该特定元素的指针来操作数组中的元素,例如以下代码

List<int> l1=new List<int>();

List<bool> l2=new List<bool>();

l1.Add(8);

l2.Add(true);

l1.Add(234);

l2.Add(true);

Console.WriteLine(l1[0]); //output=8

int* pointer = (int *) l1[0];

Console.WriteLine(*pointer); //Needs to output 8

Console.WriteLine(l2[0]); //output=true

bool* pointer2 = (bool *) l2[0];

Console.WriteLine(*pointer2); //Needs to output true

提前感谢您的帮助

I need to have a growing array, or list (the built in ones are sufficient). Furthermore I need to be able to manipulate elements in the array with pointers to that specific element for example the following code

List<int> l1=new List<int>();

List<bool> l2=new List<bool>();

l1.Add(8);

l2.Add(true);

l1.Add(234);

l2.Add(true);

Console.WriteLine(l1[0]); //output=8

int* pointer = (int *) l1[0];

Console.WriteLine(*pointer); //Needs to output 8

Console.WriteLine(l2[0]); //output=true

bool* pointer2 = (bool *) l2[0];

Console.WriteLine(*pointer2); //Needs to output true

Thanks in advance for any help

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

痴梦一场 2024-10-23 08:11:32

我正在尝试使用数组来存储数据包数据并将其传递给线程,这些线程需要能够修改数据而不破坏数组

在这种情况下,我只需传递您的 List 进入线程例程,以及线程应使用的起始和结束索引。

如果您始终按索引工作并保持在范围内,那么“破坏数组”就不会有任何问题。

Im trying to use an array to store packet data and pass it off to threads, these theads need to be able to modify the data without trashing the array

In this case, I would just pass your List<T> into the threaded routine, as well as a starting and ending index that thread should use.

Provided you always work by index, and stay within the bounds, there shouldn't be any problem with "trashing the array."

愿与i 2024-10-23 08:11:32

首先:您正在应用 C++ 方法来解决在 C# 中以不同方式解决的问题。在 C# 中,您通常不想做涉及显式指针的事情,因为它们使事情变得困难,尤其是与垃圾收集有关的时候。

也就是说,如果您必须这样做,那么您想要做的就是将整个列表(可能还有索引)作为参数以及偏移量传递给另一个线程。您还需要确保锁定 在所有访问线程中适当地列出列表,以避免脏读/写。

正确的解决方案是传递您真正想要处理的项目。引用类型通过val传递,但这仅仅意味着创建一个指向同一个堆变量的新指针。它实际上并没有在堆上创建新值。

例如:

var myList = new List<MyClass> { someInstanceofMyClass1, someInstanceofMyClass2 };
var t = new Thread(()=> SomeMethod(myList[0])); // Assuming MyClass is a reference type, the value passed here is the same instance as the one in myList
t.Start(); 
... 

First off: you are applying a C++ approach to a problem that is solved differently in C#. In C# you generally don't want to do things involving explicit pointers, because they make life difficult, especially as it pertains to garbage collection.

That said, if you must do it this way, what you'd want to do is pass the entire list (and maybe the index) as a parameter, along with an offset, to the other thread. You would also want to be sure to lock the list appropriately in all accessing threads, to avoid dirty reads/writes.

The right solution is just to pass the item that you actually want to process. Reference types are passed byval, but that just means a new pointer is created to the same heap variable. It isn't actually creating a new value on the heap.

So for example:

var myList = new List<MyClass> { someInstanceofMyClass1, someInstanceofMyClass2 };
var t = new Thread(()=> SomeMethod(myList[0])); // Assuming MyClass is a reference type, the value passed here is the same instance as the one in myList
t.Start(); 
... 
温柔一刀 2024-10-23 08:11:32

它已经按照您想要的引用类型方式工作。因此,一种可能的解决方案是创建一个类来将这些值装箱为引用类型。如果这些项目通过索引相关(我怀疑它们是相关的),那么保留一个列表来保存对两个值而不是两个列表进行分组的类型是一个好主意。就这样:

public Class MyClass
{
     public int IntValue {get;set;}
     public bool BoolValue {get;set;}
     public MyClass(int intValue, bool boolValue)
     {
          IntValue = intValue;
          boolValue = boolValue;
     }
}

List<MyClass> l1 = new List<MyClass>();
l1.Add(new MyClass(8, true));

MyClass pointer = l1[0];

Console.WriteLine(pointer.IntValue); //writes 8
Console.WriteLine(pointer.BoolValue); //writes True

It already works the way you want for reference types. Therefore one potential solution is to create a class to box these values as reference types. If the items are related by index (and I suspect they are) it's a good idea to keep one list to hold a type that groups both values rather than two lists anyway. Going with that:

public Class MyClass
{
     public int IntValue {get;set;}
     public bool BoolValue {get;set;}
     public MyClass(int intValue, bool boolValue)
     {
          IntValue = intValue;
          boolValue = boolValue;
     }
}

List<MyClass> l1 = new List<MyClass>();
l1.Add(new MyClass(8, true));

MyClass pointer = l1[0];

Console.WriteLine(pointer.IntValue); //writes 8
Console.WriteLine(pointer.BoolValue); //writes True
阳光下的泡沫是彩色的 2024-10-23 08:11:32

如果您使用的是 .NET 4,您可能需要查看 System.Collections.Concurrent 命名空间。它们提供线程安全的数据结构,可以帮助您用更少的代码实现您的目标。

If you are using .NET 4, you might want to look into the classes in System.Collections.Concurrent namespace. They provide thread-safe data structures that might help you achieve your goal with less code.

月下伊人醉 2024-10-23 08:11:32

对于您想要完成的任务(网络数据包),听起来您会受益于 System.IO.BinaryWriter 而不是列表。 (您甚至可以将 NetworkStream 传递给 BinaryWriter)

它支持查找,因此您可以返回并重写,并且您不能丢弃数组,因为它会自动增长。

就性能而言,我假设 BinaryWriter 比 List 更快,因为它写入底层 Stream,而 MemoryStream 比 List

For what you are trying to accomplish (network packets), it sounds like you would benefit from a System.IO.BinaryWriter instead of a List. (You could even pass a NetworkStream to a BinaryWriter)

It supports seeking so you can go back and re-write, and you can't trash the array since it grows automatically.

Performance-wise, I would assume BinaryWriter is faster than a List since it writes to an underlying Stream and MemoryStream is faster than a List<byte>

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文