如何消除可为空布尔值的使用
本文关键字:布尔值 何消 | 更新日期: 2023-09-27 18:34:26
我想出了这段代码,我认为它相当聪明(要求是,如果所选日期是过去的,则文本框应该是只读的,否则(今天的日期或将来的日期)它们应该是可编辑的):
bool? setReadOnly = null;
if (SelectedDateIsInThePast() && (!currentlyReadOnly)) {
setReadOnly = true;
} else if (!SelectedDateIsInThePast() && (currentlyReadOnly)) {
setReadOnly = false;
}
if (setReadOnlyToTrue.HasValue) {
foreach (Control ctrl in tableLayoutPanelPlatypus.Controls) {
if (ctrl is TextBox) {
tb = (TextBox)ctrl;
tb.ReadOnly = setReadOnlyToTrue.Value;
}
}
}
。但是发现可空布尔值在我的同伴中是"数据类型不受欢迎的"。
有没有一种不复杂的方法来做同样的事情(只有在需要更改只读值时才遍历控件?当然,我可以简单地设置它们,而不管它们是否需要这样设置:
if (SelectedDateIsInThePast()) {
setReadOnly = true;
} else {
setReadOnly = false;
}
foreach (Control ctrl in tableLayoutPanelPlatypus.Controls) {
if (ctrl is TextBox) {
tb = (TextBox)ctrl;
tb.ReadOnly = setReadOnly;
}
}
。但我不喜欢执行模拟操作,如果合理地避免它们的话。
将
循环分解为方法,并且仅在您设置的情况下调用该方法 setReadOnly
:
if (SelectedDateIsInThePast() && (!currentlyReadOnly)) {
SetReadOnly(true);
} else if (!SelectedDateIsInThePast() && (currentlyReadOnly)) {
SetReadOnly(false);
}
您可以使用 |=
、&=
和两个不可为空的布尔值来实现相同的要求:
bool forceReadOnly = SelectedDateIsInThePast() && (!currentlyReadOnly);
bool clearReadOnly = !(!SelectedDateIsInThePast() && (currentlyReadOnly));
foreach (Control ctrl in tableLayoutPanelPlatypus.Controls) {
if (ctrl is TextBox) {
tb = (TextBox)ctrl;
tb.ReadOnly |= forceReadOnly;
tb.ReadOnly &= clearReadOnly;
}
}
我认为一个可为空的布尔值很好......但另一种方式是:
public enum ControlState
{
Unknown = 0,
DateInPast,
DateInFuture
}
....
var state = ControlState.Unknown;
if (SelectedDateIsInThePast() && (!currentlyReadOnly)) {
state = ControlState.DateInPast;
} else if (!SelectedDateIsInThePast() && (currentlyReadOnly)) {
state = ControlState.DateInFuture;
}
if (state != ControlState.Unknown) {
foreach (Control ctrl in tableLayoutPanelPlatypus.Controls) {
if (ctrl is TextBox) {
tb = (TextBox)ctrl;
tb.ReadOnly = setReadOnlyToTrue.Value;
}
}
}
使用具有三个独立、有意义的状态的枚举?
enum ShouldSetState
{
No,
SetReadOnly,
SetReadable
}
然后做
ShouldSetState setState = ShouldSetState.No;
if (SelectedDateIsInThePast() && (!currentlyReadOnly)) {
setState = ShouldSetState.SetReadOnly;
} else if (!SelectedDateIsInThePast() && (currentlyReadOnly)) {
setState = ShouldSetState.SetReadable;
}
if (setState != ShouldSetState.No) {
foreach (Control ctrl in tableLayoutPanelPlatypus.Controls) {
if (ctrl is TextBox) {
tb = (TextBox)ctrl;
tb.ReadOnly = setState == ShouldSetState.SetReadOnly;
}
}
}
您的代码可以在不使用可为空的布尔值的情况下变得更加简洁:
bool inThePast = SelectedDateIsInThePast();
if (currentlyReadOnly != inThePast )
{
currentlyReadOnly = inThePast;
foreach(var tb in tableLayoutPanelPlatypus.Controls.OfType<TextBox>())
tb.ReadOnly = currentlyReadOnly;
}
此外,如果必须执行大量此类 UI 操作,则可以考虑数据绑定。