Рейтинг:
7
Richard Deeming
По умолчанию параметры передаются по значению. Это означает, что любые изменения, внесенные в значение параметров внутри метода, не будут видны вызывающему методу.
Передача Параметров - Руководство По Программированию На C# | Microsoft Docs[^]
Передача параметров в C#[^]
Если вы хотите, чтобы изменения были видны вызывающему методу, то вам нужно передать параметры по ссылке. Вы делаете это, используя либо ref
или out
модификаторы.
ключевое слово ref - ссылка на C# | Microsoft Docs[^]
модификатор параметров out - Справочник по C# | Microsoft Docs[^]
Например:
public ActionResult Index()
{
const string barcodeTopParent = "DT-COMPSTART";
const string barcodeMiddleParent = "DB-TEST";
const string barcodeBottomParent = "SP-SLD";
string strTopBarCode, strMiddleBarCode, strBottomBarCode;
helper.ReadBarcodeFromFile(file.FullName, out strTopBarCode, out strMiddleBarCode, out strBottomBarCode);
if (strTopBarCode == barcodeTopParent || strMiddleBarCode == barcodeMiddleParent || strBottomBarCode == barcodeBottomParent)
{
...
}
}
public void ReadBarcodeFromFile(string _Filepath, out string strTopBarCode, out string strMiddleBarCode, out string strBottomBarCode)
{
string[] barcodes = BarcodeScanner.Scan(_Filepath, BarcodeType.Code39);
if (barcodes.Length != 0)
{
strTopBarCode = barcodes[0];
strMiddleBarCode = barcodes[1];
strBottomBarCode = barcodes[2];
}
else
{
strTopBarCode = null;
strMiddleBarCode = null;
strBottomBarCode = null;
}
}
NB: Есть некоторые случаи, когда вы не можете пройти по ссылке - особенно
async
методы и методы итератора.
Передача по ссылке также часто считается "запахом кода", и ее следует избегать везде, где это возможно. Вы можете либо создать определенный тип для хранения нескольких возвращаемых значений, либо вернуть
ValueTuple
вместо.
Типы кортежей - руководство по C# | Microsoft Docs[
^]
public ActionResult Index()
{
const string barcodeTopParent = "DT-COMPSTART";
const string barcodeMiddleParent = "DB-TEST";
const string barcodeBottomParent = "SP-SLD";
var barcodes = helper.ReadBarcodeFromFile(file.FullName);
if (barcodes.topBarCode == barcodeTopParent || barcodes.middleBarCode == barcodeMiddleParent || barcodes.bottomBarCode == barcodeBottomParent)
{
...
}
}
public (string topBarCode, string middleBarCode, string bottomBarCode) ReadBarcodeFromFile(string _Filepath)
{
string[] barcodes = BarcodeScanner.Scan(_Filepath, BarcodeType.Code39);
if (barcodes.Length != 0) return (barcodes[0], barcodes[1], barcodes[2]);
return default;
}
AskalotLearnalot
Привет, спасибо за ваше время и объяснение. Второе предположение привело к той же ошибке. Однако первый из них решил проблему. По вашему опыту, есть ли у "запаха кода" побочные эффекты.
Richard Deeming
Что вы подразумеваете под "той же самой ошибкой"? Второй вариант будет только возвращать null
значения, если Scan
метод не вернул никаких штрих-кодов.
"Запах кода" - это то, что не обязательно неправильно, но может указывать на более глубокую проблему. В этом случае ваш метод хочет вернуть несколько значений; есть лучшие способы сделать это, чем передача по ссылке; и альтернативы приводят к коду, который более понятен и понятен.
AskalotLearnalot
Привет спасибо за повтор в обоих случаях я запустил ту же папку, которая содержит штрих-коды, так что это не проблема метода сканирования.
Richard Deeming
Попробуй перешагнуть через него. ReadBarcodeFromFile
метод проверки того, что он возвращает, а затем исследует возвращаемое значение в Index
метод после его возвращения.
AskalotLearnalot
так что происходит та же проблема, что и у меня в вопросе. но "запах кода" работает отлично.
Richard Deeming
Так ты говоришь, что ... ReadBarcodeFromFile
метод считывает массив по крайней мере из трех строк; ни одна из строк не является null
; но когда метод возвращается, и ваш if
оператор выполняется, возвращаемые значения изменились на null
?
Должно быть, происходит что-то еще. Возвращаемые значения кортежа работают для всех остальных.
AskalotLearnalot
Исправьте, прежде чем я перейду к последнему } в файле ReadBarcodeFromFile, если я перейду к результату действия и Гуверу над штрих-кодами var, он имеет 3 элемента. Однако strTopBarCode, strMiddleBarCode.. остается без значения после того,как он пропылесосится, а затем, когда я выхожу из метода, они получают значение null. В моем случае это были значения get, а затем, когда я выхожу из метода, им присваивается null, который я просто не знал, как передать/добавить значения обратно.
Richard Deeming
Второе решение не имеет вызываемых переменных strTopBarCode
или strMiddleBarCode
Так что они никак не могут быть такими . null
- потому что их не существует!
AskalotLearnalot
так что эта публика (строка topBarCode, middleBarCode строку, строку bottomBarCode)
и как это будет работать для меня в заявлении if. Это ноль я не знаю как
AskalotLearnalot
так что любая идея о том, как заставить второе решение работать. или это тот случай, когда работает только pass by ref.
Richard Deeming
Как я уже говорил, Если первое решение работает, то и второе тоже.
Вы, кажется, путаете решения и смотрите на несвязанные переменные.
AskalotLearnalot
лол, это должно сработать. Я буду делать больше копать спасибо за ваше время и помощь.
Рейтинг:
2
Richard MacCutchan
Вы не фиксируете возвращаемые значения из вызова ReadBarcodeFromFile
, и дополнительные три параметра никогда не используются.
helper.ReadBarcodeFromFile(file.FullName, strTopBarCode, strMiddleBarCode, strBottomBarCode);
Код должен быть таким
Array barcodes = helper.ReadBarcodeFromFile(file.FullName) // -> not used, strTopBarCode, strMiddleBarCode, strBottomBarCode);
if (barcodes != null)
{
// process the barcodes
}
То
ReadBarcodeFromFile
метод должен быть
public Array ReadBarcodeFromFile(string _Filepath)
{
String[] barcodes = BarcodeScanner.Scan(_Filepath, BarcodeType.Code39);
if (barcodes.Length != 0)
{
return barcodes;
}
return null;
}
AskalotLearnalot
Спасибо за вашу помощь. Однако этот подход привел к тому же самому вопросу.
Richard MacCutchan
Тогда вы, должно быть, делаете что-то не так. Но поскольку вы не показали свой код, я не могу догадаться, что это может быть.