#c# #properties
Вопрос:
Такова ситуация, у меня есть класс с двумя свойствами. Если значение Sex равно нулю, то оно устанавливается в зависимости от значения SexString, проблема заключается в доступе к значению Sex, оно ошибается, когда я пытаюсь получить к нему доступ. Есть какие-нибудь идеи о том, что я делаю не так?
public class Person
public string SexString { get; set; }
public int? Sex
{
get { return this.Sex.Value; }
set
{
if (value == null)
{
if (this.SexString.Trim().ToLower() == "female")
{
this.Sex = 1;
}
else if (this.SexString.Trim().ToLower() == "male")
{
this.Sex = 0;
}
else
{
this.Sex = 3;
}
}
else if (value <= 3 amp;amp; value >= 0)
{
this.Sex = value;
}
else
{
this.Sex = 3;
}
}
}
Комментарии:
1.
return this.Sex.Value;
причины переполнения стека :this.Sex
вызовыthis.Sex
, которые вызываютthis.Sex
и т. Д. Используйте резервное поле (скажем,int? m_Sex
), чтобы разорвать этот порочный круг вызовов
Ответ №1:
У вас проблема с переполнением стека: всякий раз, когда вы звоните
this.Sex
внутри Sex
свойства он начинает вызывать Sex
свойство, которое вызывает this.Sex
, которое вызывает Sex
и т. Д.
Попробуйте использовать резервное поле:
private int? m_Sex;
public int? Sex {
get => m_Sex.HasValue ? m_Sex.Value : 3;
set {
if (value == null)
if ("female".Equals(SexString, StringComparison.OrdinalIgnoreCase))
m_Sex = 1;
else if ("male".Equals(SexString, StringComparison.OrdinalIgnoreCase))
m_Sex = 2; //TODO: check this value: is it 0 or 2?
else
m_Sex = 3;
else if (value >= 0 amp;amp; value <= 3)
m_Sex = value;
else
m_Sex = 3;
}
}
Примечание: Взгляните на ISO/IEC 5218 — стандартные половые коды:
- 0 = Неизвестно
- 1 = Мужчина
- 2 = Женщина
- 9 = Не применимо
Может быть, вам не стоит изобретать свои собственные коды? Если вы придерживаетесь стандарта, вы можете легко реализовать Sex
свойство:
private int m_Sex;
public int Sex {
get => m_Sex;
set {
m_Sex = value >= 0 amp;amp; value <= 2 || value == 9
? value
: throw new ArgumentOutOfRange(nameof(value));
}
}
Что касается SexString
, вы можете получить его из m_Sex
:
public string SexString {
get => m_Sex == 0 ? "Unknown"
: m_Sex == 1 ? "Male"
: m_Sex == 2 ? "Female"
: "Not applicable";
set {
if ("unknown".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"not known".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"?".Equals(value, StringComparison.OrdinalIgnoreCase))
m_Sex = 0;
else if ("male".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"man".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"m".Equals(value, StringComparison.OrdinalIgnoreCase))
m_Sex = 1;
else if ("female".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"woman".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"w".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"f".Equals(value, StringComparison.OrdinalIgnoreCase))
m_Sex = 2;
else if (string.IsNullOrWhiteSpace(value) ||
"-".Equals(value, StringComparison.OrdinalIgnoreCase) ||
"Not applicable".Equals(value, StringComparison.OrdinalIgnoreCase))
m_Sex = 9;
else
throw new ArgumentException("Not a valid sex definition", nameof(value));
}
}