Below is a Win32 Console App procedure that demonstrates the dependence of various pointers on an array. A change to the values in the original array (model) by for example uncommenting the lines marked '// uncomment ...' results in a change to the output. My question is how do I get or mimic this behaviour in a C# managed code environment (ie without using unsafe and pointers)?
#include "stdafx.h"
#include <iostream>
using namespace std;
int _tmain(int argc, _TCHAR* argv[])
{
float model[100];
for(int i = 0; i < 100; i++) { model[i] = i; }
// uncomment these to alter the results
//model[5] = 5000;
//model[20] = 20000;
//model[38] = 38000;
static const int componentCount = 5;
float* coefs = model; // coefs points to model[0]
float* mean = coefs + componentCount; // mean points to model[0 + componentCount] == model[5]
float* cov = mean + 3*componentCount; // cov points to model[0 + componentCount + 3*componentCount] == model[20]
int ci = 2;
float* c = cov + 9*ci; // c points to model[0 + componentCount + 3*componentCount + 9*ci] == model[38]
int i = 0;
cout <<"model : "<< model[i] << endl; // 0
cout <<"coefs : "<< coefs[i] << endl; // 0
cout <<"mean : "<< mean[i] << endl; // 5 (or 5000)
cout <<"cov : "<< cov[i] << endl; // 20 (or 20000)
cout <<"ci : "<< ci << endl; // 2
cout <<"c : "<< c[i] << endl; // 38 (or 38000)
cin.get(); }
You can do the same thing in C# without unsafe code:
struct ArrayPointer<T>
{
private T[] array;
private int offset;
public ArrayPointer(T[] array) : this(array, 0)
{
}
private ArrayPointer(T[] array, int offset)
{
Debug.Assert(array != null);
Debug.Assert(offset >= 0);
Debug.Assert(offset < array.Length);
this.array = array;
this.offset = offset;
}
public static ArrayPointer<T> operator+(ArrayPointer<T> p1, int p2)
{
return new ArrayPointer<T>(p1.array, p1.offset + p2);
}
And so on. Define operators for addition, subtraction, increment, decrement, comparison, indexing, conversion from arrays, and so on. Then you can say:
int[] arr = whatever;
ArrayPointer<int> pointer = arr;
pointer+=2;
pointer--;
int x = pointer[3];
and so on.
This approach has a lot of nice properties. For example, you can do a debug assert if you ever compare p1 > p2 when p1 and p2 are pointers to the interiors of different arrays. That is almost always a bug in C, but a hard one to catch.
You could write a class that represents an array with some offset, similar to the one below. Additionaly, you might want it to implement ICollection<T>
or at least IEnumerable<T>
.
class ArrayWithOffset<T>
{
T[] m_array;
int m_offset;
public ArrayWithOffset(T[] array, int offset)
{
m_array = array;
m_offset = offset;
}
public T this[int i]
{
return m_array[offset + i]
}
}
而不是一个参数,指向数组项的指针,使用参数对(数组,偏移量)。
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.