Имеется старый код на VB.Net, который портируется на C#. В процессе возникла проблема с портированием Strings.Format.
В коде используются
именованные форматы даты времени,
именованные числовые форматы и
определяемые пользователем строковые форматы
(так и не понял, почему на странице документации по Strings.Format не доступна вся информация об именованных форматах).
Проблема заключается в том, что вышеуказанные форматы сохраняются в двоичных конфигурационных файлах для которых необходимо обеспечить обратную совместимость. К примеру, имеется такой VB метод:
Public Function StringConvert(ByVal sValue As String, ByVal sFormatString As String) As String
Dim RetWert As String
Dim neuWert As String = Trim(sValue)
Dim format As String = Trim(sFormatString)
If format = "String" Then
RetWert = neuWert
ElseIf format = "General Date" Or
format = "Long Date" Or
format = "Short Date" Or
format = "Medium Date" Or
format = "Long Time" Or
format = "Medium Time" Or
format = "Short Time" Then
If IsDate(sValue) Then
RetWert = Format(CDate(neuWert), format)
Else
RetWert = ""
End If
ElseIf format = "General Number" Or
format = "Currency" Or
format = "Fixed" Or
format = "Standard" Or
format = "Percent" Or
format = "Scientific" Then
If IsNumeric(sValue) Then
RetWert = Format(CDbl(neuWert), format)
Else
RetWert = ""
End If
ElseIf format = "Yes/No" Or
format = "True/False" Or
format = "On/Off" Then
If IsNumeric(sValue) Then
RetWert = Format(CBool(neuWert), format)
Else
RetWert = ""
End If
Else
If InStr(format, "@") > 0 Or
InStr(format, "&") > 0 Or
InStr(format, "<") > 0 Or
InStr(format, ">") > 0 Or
InStr(format, "!") > 0 Then
RetWert = Format(neuWert, format)
ElseIf InStr(format, "c") > 0 Or InStr(format, "y") > 0 Or
InStr(format, "d") > 0 Or InStr(format, "h") > 0 Or
InStr(format, "w") > 0 Or InStr(format, "s") > 0 Or
InStr(format, "m") > 0 Or InStr(format, "t") > 0 Or
InStr(format, "q") > 0 Or InStr(format, "+") > 0 Then
If IsNumeric(sValue) Then
RetWert = Format(CDate(neuWert), format)
Else
RetWert = ""
End If
ElseIf InStr(format, " ") > 0 Or InStr(format, "%") > 0 Or
InStr(format, "0") > 0 Or InStr(format, "-") > 0 Or
InStr(format, "#") > 0 Or InStr(format, "E") > 0 Or
InStr(format, ".") > 0 Or InStr(format, "e") > 0 Or
InStr(format, ",") > 0 Or InStr(format, "+") > 0 Then
If IsNumeric(sValue) Then
RetWert = Format(CDbl(neuWert), format)
Else
RetWert = ""
End If
Else
RetWert = CStr(neuWert)
End If
End If
StringConvert = RetWert
End Function
Пробовал создать свой IFormatProvider для форматирования DateTime, но он просто преобразует символы строковых форматов дат (в примере ниже это h
и t
). Конечно можно импортировать пространство имён Microsoft.VisualBasic и использовать метод далее, но (насколько я понимаю) этот подход не будет работать с .Net Core, что критично.
Имеется ли аналог Strins.Format в C#? Может быть есть какая-либо библиотека (.Net Standard)? Каким образом, по Вашему мнению, можно оптимально решить эту задачу?
"Поиграться" можно здесь.
public class VBDateTimeFormatProvider : IFormatProvider, ICustomFormatter
{
public object GetFormat(Type formatType)
{
return formatType == typeof(ICustomFormatter)
? this : null;
}
private readonly Dictionary<string, string> _map = new Dictionary<string, string>()
{
{"General Date", "G"},
{"Long Date", "D"},
{"Short Date", "d"},
{"Medium Date", "D"},
{"Long Time", "T"},
{"Medium Time", "T"},
{"Short Time", "t"}
};
public string Format(string format, object arg, IFormatProvider formatProvider)
{
format = format.Trim();
return _map.ContainsKey(format)
? DateTime.Parse(arg.ToString()).ToString(_map[format], CultureInfo.CurrentCulture)
: string.Empty;
}
}
// var dt = new DateTime(2020, 1, 1).ToString();
// Console.WriteLine(DateTime.Parse(dt).ToString(format, new VBDateTimeFormatProvider()));
// выводит: "S12orA DaAe"
VB.NET использует тот же .NET, что и C#. Так что берёшь проект на C#, идешь в references и добавляешь библиотеку Microsoft.VisualBasic
. После чего используешь сколько хочешь.
Кстати, по твоей же ссылке написано:
.NET Core 3.1, 3.0
.NET Framework 4.8, 4.7.2, 4.7.1, 4.7, 4.6.2, 4.6.1, 4.6, 4.5.2, 4.5.1, 4.5, 4.0, 3.5, 3.0, 2.0, 1.1
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
Нужно вывести произведение чисел <50, не используя условие if для проверки значения pr в выводе :
Есть компонент, который принимает один параметр для отображенияВозникла необходимость отрендерить его не в шаблоне, а в методе (для последующей...
Есть класс, который отвечает за установку двунаправленного соединения между процессами(через pipe), ввод в stdin дочернего процесса и вывод через...
Необходимо нарисовать линию со сложным паттерном в виде символа при помощи QPainterКак в примере ниже