Использование Visual Studio 2017, C #
Итак, у меня есть класс, который хранит данные в нескольких двумерных или трехмерных массивах из другого метода.Однако, когда я фактически изменяю одно из значений (и только одно из значений), изменение любых других значений в экземпляре класса также изменяет это значение.Ничто не является статичным, и ничего не происходит между изменением одного значения и изменением другого.
Класс;
public class TestResults
{
public int finalResult;
public float[,] activations;
public float[,] magnitudes;
public float[, ,] weights;
public float[,] biases;
public int actual;
public TestResults(int newF, float[,] newAct, float[,] newMag, float[, ,] newW, float[,] newB, int newA)
{
finalResult = newF;
activations = newAct;
magnitudes = newMag;
weights = newW;
biases = newB;
actual = newA;
}
}
Проблемный сценарий (
for (int l = 1; l < 4; l++)
{
for (int i = 0; i < nodeCounts[l]; i++)
{
float newValue = 0;
for (int j = 0; j < nodeCounts[l - 1]; j++)
{
float inputValue = nodes[l - 1, j].value;
float newMag = (inputValue * nodes[l, i].weights[j]);
newValue += newMag;
//Update test results
result.weights[l, i, j] = nodes[l, i].weights[j];
}
nodes[l, i].value = Squish(newValue + nodes[l, i].bias);
//Update test results
result.activations[l, i] = nodes[l, i].value; //This value right here is what is causing the issues. Debugging showed that the value is correct (equal to nodes[l, i].value) right after this line, but after the next line the value changes, and it changes again after the next.
result.magnitudes[l, i] = newValue;
result.biases[l, i] = nodes[l, i].bias;
float debug = result.activations[l, i];
}
}
Короче говоря, значение
result.activations[l, i]
должно оставаться эквивалентным
nodes[l, i].value
... но по какой-то причине это не так. Если это помогает, значение nodes[l, i].value
всегда между 0 и 1 (отладка показывает, что это работает правильно), и все же значение result.activations[l, i]
всегда заканчивается как отрицательное целое число (типичное значение result.biases[l, i]
). Я попытался изменить все типы значений надесятичное число (в этом состоянии они являются числами с плавающей точкой), но результат был таким же.
Я уничтожил кнопку поиска Google, чтобы обнаружить, что никто до этого не сталкивался с этой проблемой. На данный момент я начинаюЯ думаю, что это ошибка самой Visual Studio. Любая помощь в решении этой проблемы будет признательна. Перезапуск Visual Studio и моего ноутбука ничего не сделал. Спасибо, Райан Г.
РЕДАКТИРОВАТЬ: Вотполный метод, в том числе тЦикл я выделил ранее в этом вопросе.Надеюсь, это даст лучший контекст.
TestResults TestNetwork(byte[] image, int[] nodeCounts, Node[ , ] nodes, int actual)
{
float[,] resultsFloats = new float[nodeCounts.Count(), nodes.GetLength(1)];
TestResults result = new TestResults(0, resultsFloats, resultsFloats, new float[nodeCounts.Count(), nodes.GetLength(1), nodes.GetLength(1)], resultsFloats, 0);
int finalResult = 0;
//Match image values to input nodes
for(int i = 0; i < nodeCounts[0]; i++)
{
nodes[0, i].value = (float)image[i] / 255;
//Update test results
result.activations[0, i] = nodes[0, i].value;
}
//Calculate values for second, third, and fourth layers
for (int l = 1; l < 4; l++)
{
for (int i = 0; i < nodeCounts[l]; i++)
{
float newValue = 0;
for (int j = 0; j < nodeCounts[l - 1]; j++)
{
float inputValue = nodes[l - 1, j].value;
float newMag = (inputValue * nodes[l, i].weights[j]);
newValue += newMag;
//Update test results
result.weights[l, i, j] = nodes[l, i].weights[j];
}
nodes[l, i].value = Squish(newValue + nodes[l, i].bias);
//Update test results
result.activations[l, i] = nodes[l, i].value;
result.magnitudes[l, i] = newValue;
result.biases[l, i] = nodes[l, i].bias;
float debug = result.activations[l, i];
}
}
//Decide result
float mag = -1;
for (int i = 0; i < 10; i++)
{
if (nodes[nodeCounts.Count() - 1, i].value > mag)
{
finalResult = i;
mag = nodes[nodeCounts.Count() - 1, i].value;
}
}
result.finalResult = finalResult;
result.actual = actual;
return result;
}
Узел - это просто еще один класс, в котором мне нужно хранить больше данных.Как видно в верхней части функции, когда инициализируется экземпляр TestResults, для каждого из массивов выделяется память, используя другие значения.
РЕДАКТИРОВАТЬ 2: Просто запустил еще один тест:
TestResults dTR = new TestResults(0, new float[2, 2], new float[2, 2], new float[2, 2, 2], new float[2, 2], 0);
dTR.activations[0, 0] = 1;
dTR.magnitudes[0, 0] = 2;
dTR.biases[0, 0] = 3;
Console.WriteLine(dTR.activations[0, 0] + ", " + dTR.magnitudes[0, 0] + ", " + dTR.biases[0, 0]);
Выводит «1, 2, 3», как и должно быть.Я не понимаю, чем это отличается от моего проблемного кода.
ОБНОВЛЕНИЕ: После того, как я сдался и захотел спать, я понял, что основная проблема заключалась в том, что result.activations[l, i]
менялитак как я менял значения после того, как я уже изменил свое значение.Итак, пытаясь сделать очевидное, я просто помещаю строку, где я изменяю ее значение, после строк, где я изменяю все остальные значения.Работал как шарм.
Я вижу, что это решение с клейкой лентой, и я хочу понять, почему это все еще происходит, поэтому я обновлю этот пост позже, когда попробую некоторые изПредлагаемые исправления в ответах.