gpt4 book ai didi

c# - 从 12 个月的 bool 值列表中创建日期范围字符串

转载 作者:行者123 更新时间:2023-11-30 21:53:42 25 4
gpt4 key购买 nike

我有一个包含 12 个 bool 属性的 C# 类;

可用一月,可用二月,可用三月,可用四月...等

这个类的每个实例都可以有任意数量的它们为真,并且通常它们按顺序运行。 IE。 AvailableFeb - AvailableApr 将是真实的,但没有其他人。有时只有一个 bool 为真,即仅在一个月内可用。有时它们都会存在,即全年可用。

有时,这是棘手的一点,它们会有两个范围,即 2 月至 4 月和 8 月至 10 月可用。

我正在尝试编写一个函数来返回一个字符串来表示所做的选择。

我只选择了 1 个 bool 值(例如:“仅限二月”)。

所选范围(例如):“Jan-Mar”。

多个范围(例如):“Jan-Mar, Aug-Nov”。

混合单一和范围(例如):“Jan-Mar, Sep”。

全部选择:“全年”。

范围是指连续月份被指定为真,例如Jan、Feb、Mar 为真应导致 Jan-Mar。

我曾尝试使用带有简单条件检查的循环,但它很困惑,我无法正确处理,我很遗憾将它们存储为单独的属性而不是 int 数组,但我现在坚持这样做。我想知道是否有一种方法可以使用反射然后循环将 bool 存储在另一个属性中。到目前为止还没有运气。非常感谢任何帮助!

谢谢

最佳答案

如果你想稍微改变一下你的类(class),那就按照这种方式做吧!

您可以拥有 12 个属性并将它们映射到单个 int 数组中。所以你有长度为 12 的 int 数组。当 intArray[0] = 1 意味着第一个月可用。如果 intArray[0] = 0 表示第一个月不可用,依此类推。

您将此 int 数组转换为字符串,其中以 16 为基数表示每个月的基于 1 的索引,但如果它不可用,则改为使用 0。稍后我们使用字典通过给出月份的编号来获取月份的名称。

示例 1:

"003456000a00"

这意味着月份 3th,4th,5th,6tha = 10th 可用。然后使用正则表达式解析它并找到匹配项。正则表达式模式将为 [^0]+。表示它匹配除 0 之外的任何字符。

所以正则表达式会给我们这个匹配项。

Match 1 : 3456
Match 2 : a

第一个匹配长度大于 1 表示它是一个月份范围。所以我们取第一个字符和最后一个字符。我们用 - 加入他们。此处为 36。所以 match 1 应该变成

Mar-Jun

第二个匹配长度仅为 1 表示它是一个月。所以应该变成

Oct

因为我们有两个匹配项,所以我们用 , 加入它们,最后输出是 Mar-Jun , Oct

示例 2:

"020000000000"

匹配

Match 1 : 2

因为我们只有 1 场比赛,比赛长度为 1,所以这应该变成

Feb Only

示例 3:

"023456780000"

匹配

Match 1 : 234567

这只是一场比赛,但这场比赛的长度不止一场。所以我们只取 27 并用 - 加入它们。

Feb-Jul

示例 4:

"123456789abc"

匹配

Match 1 : 123456789abc

如您所见,我们有所有月份。这场比赛的长度是12所以应该是

Year round

示例 5:

"123456000abc"

匹配

Match 1 : 123456
Match 2 : abc

这里有两场比赛。它可以是 Jan-Jun 、Oct-Dec 但更好的表示(如您在评论中提到的)是 Oct-Jun。那应该是 abc123456。所以我们检查最后一场比赛是否以 c 结尾,第一场比赛是否以 1 开始,然后我们将最后一场比赛与第一场比赛连接起来。

Oct-Jun

代码:

如你所见,它会变得简单。

internal class AvailableYear
{
private readonly int[] _available;
private static readonly Regex MatchTrue = new Regex("[^0]+");
private static readonly Dictionary<string, string> GetName = new Dictionary<string, string>
{
{"1","Jan" },
{"2","Feb" },
{"3","Mar" },
{"4","Apr" },
{"5","May" },
{"6","Jun" },
{"7","Jul" },
{"8","Aug" },
{"9","Sep" },
{"a","Oct" },
{"b","Nov" },
{"c","Dec" },
};

public AvailableYear(params int[] available)
{
if (available.Length > 12) throw new IndexOutOfRangeException("given parameters should not exceed 12 months.");

_available = available;
}

public int AvaialableJan
{
get { return _available[0]; }
set { _available[0] = value; }
}

public int AvailableFeb
{
get { return _available[1]; }
set { _available[1] = value; }
}
public int AvailableMar
{
get { return _available[2]; }
set { _available[2] = value; }
}
public int AvailableApr
{
get { return _available[3]; }
set { _available[3] = value; }
}
public int AvaialableMay
{
get { return _available[4]; }
set { _available[4] = value; }
}
public int AvaialableJun
{
get { return _available[5]; }
set { _available[5] = value; }
}
public int AvaialableJul
{
get { return _available[6]; }
set { _available[6] = value; }
}
public int AvaialableAug
{
get { return _available[7]; }
set { _available[7] = value; }
}
public int AvaialableSep
{
get { return _available[8]; }
set { _available[8] = value; }
}
public int AvaialableOct
{
get { return _available[9]; }
set { _available[9] = value; }
}
public int AvaialableNov
{
get { return _available[10]; }
set { _available[10] = value; }
}
public int AvaialableDec
{
get { return _available[11]; }
set { _available[11] = value; }
}

public override string ToString()
{
string values = string.Join("", _available.Select((x, i) => x == 0 ? "0" : Convert.ToString(i + 1, 16)));
var matches = MatchTrue.Matches(values).Cast<Match>().Select(x => x.Value).ToList();

if (matches.Count == 0)
{
return "None";
}
if (matches[0].Length == 12)
{
return "Year round";
}
if (matches.Count == 1 && matches[0].Length == 1)
{
return GetName[matches[0]] + " Only";
}
else
{
if (matches.First().StartsWith("1") && matches.Last().EndsWith("c"))
{
matches[0] = matches.Last() + matches.First();
matches.RemoveAt(matches.Count - 1);
}

List<string> output = new List<string>();

foreach (var match in matches)
{
if (match.Length == 1)
{
output.Add(GetName[match]);
}
else
{
output.Add(GetName[match.First().ToString()] + "-" +
GetName[match.Last().ToString()]);
}
}

return string.Join(", ", output);
}
}
}

这是测试。

static void Main()
{
AvailableYear ay = new AvailableYear(1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 0);
Console.WriteLine(ay.ToString());

// Output : Jan , Apr-Jul , Nov
}

更新:

如果你想在构造函数中分配 bool 值,你可以将构造函数更改为此。

public AvailableYear(params bool[] available)
{
if (available.Length > 12) throw new IndexOutOfRangeException("given parameters should not exceed 12 months.");

_available = available.Select(Convert.ToInt32).ToArray();
}

然后像这样创建实例。无需每次都编写 Convert.ToInt32。

return new AvailableYear(AvailableJan, AvailableFeb, AvailableMar...., AvailableDec).ToString();

关于c# - 从 12 个月的 bool 值列表中创建日期范围字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33721535/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com