【问题标题】:Increment string letters and numbers only c#仅增加字符串字母和数字c#
【发布时间】:2020-02-26 11:27:32
【问题描述】:

这里问了一个类似的问题: Increment a string with both letters and numbers 除了它只增加字符串中的数字外,我想增加 both 数字和字母,并且只增加字母和数字,而不是像 ;+-*:= 字符这样的其他任何东西。

例子:

Z006GZYBA1 => Z006GZYBA2
        A9 => AA 
        AZ => B0 
1ZZZZZZZZZ => 2000000000

编辑:我尝试过的:

 public static string IncrementString(this string input)
    {
        string rtn = "A";
        if (!string.IsNullOrWhiteSpace(input))
        {
            bool prependNew = false;
            var sb = new StringBuilder(input.ToUpper());
            for (int i = (sb.Length - 1); i >= 0; i--)
            {
                if (i == sb.Length - 1)
                {
                    var nextChar = Convert.ToUInt16(sb[i]) + 1;
                    if (nextChar > 90)
                    {
                        sb[i] = 'A';
                        if ((i - 1) >= 0)
                        {
                            sb[i - 1] = (char)(Convert.ToUInt16(sb[i - 1]) + 1);
                        }
                        else
                        {
                            prependNew = true;
                        }
                    }
                    else
                    {
                        sb[i] = (char)(nextChar);
                        break;
                    }
                }
                else
                {
                    if (Convert.ToUInt16(sb[i]) > 90)
                    {
                        sb[i] = 'A';
                        if ((i - 1) >= 0)
                        {
                            sb[i - 1] = (char)(Convert.ToUInt16(sb[i - 1]) + 1);
                        }
                        else
                        {
                            prependNew = true;
                        }
                    }
                    else
                    {
                        break;
                    }

                }
            }
            rtn = sb.ToString();
            if (prependNew)
            {
                rtn = "A" + rtn;
            }
        }

        return rtn.ToUpper();
    }

【问题讨论】:

  • 所以向我们展示您迄今为止尝试过的代码并解释为什么它没有按预期工作。
  • 允许的字母范围是多少 - 只是 A .. Z? (即 36 个不同的符号,包括数字)。字符串的最大长度是多少?
  • 基本上你应该将每个字符串表示为一个可以计算的数字。例如,添加1 并将其转换回字符串。但是,这种转换的工作原理远远超出了这里的一个简单问题 - 特别是因为您没有提供任何自己的想法或代码来显示您已经尝试过的内容。
  • 顺便问一下,你的用例到底是什么?
  • @FranzGleichmann 我收到了这个 ID,并被告知下一个引用将是一个递增的值,它会立即创建并且可以安全使用。所以我需要自己增加它。

标签: c# base36


【解决方案1】:

这应该可以工作(方法是IncrementBase36(),但我将它放在控制台应用程序中用于演示目的):

using System;

namespace Demo
{
    class Program
    {
        static void Main()
        {
            Console.WriteLine(IncrementBase36("Z006GZYBA1"));
            Console.WriteLine(IncrementBase36("A9"));
            Console.WriteLine(IncrementBase36("AZ"));
            Console.WriteLine(IncrementBase36("1ZZZZZZZZZ"));
        }

        public static string IncrementBase36(string numberBase36)
        {
            var digits = numberBase36.ToCharArray();
            bool carry = true;

            for (int i = digits.Length - 1; i >= 0; --i)
            {
                if (carry)
                {
                    if (digits[i] == 'Z')
                    {
                        digits[i] = '0';
                    }
                    else
                    {
                        if (digits[i] == '9')
                            digits[i] = 'A';
                        else
                            ++digits[i];

                        carry = false;
                    }
                }
            }

            if (carry)
                return '1' + new string(digits);
            else
                return new string(digits);
        }
    }
}

【讨论】:

    【解决方案2】:

    您只需使用radix = 3610 digist + 26 字母)将1 添加到数字:

    private static string IncrementString(string value) {
      if (null == value)
        throw new ArgumentNullException(nameof(value));
    
      HashSet<char> skip = new HashSet<char>(";+-*:=");
      int shift = 1;
      bool added = false; 
      StringBuilder sb = new StringBuilder(value.Length + 1);
    
      foreach (char c in value.Reverse()) {
        if (skip.Contains(c)) {
          sb.Append(c);
    
          continue;
        }
    
        int v = (c >= '0' && c <= '9') ? c - '0'
              : (c >= 'a' && c <= 'z') ? c - 'a' + 10
              : (c >= 'A' && c <= 'Z') ? c - 'A' + 10
              : throw new FormatException("Invalid symbol");
    
        added = true;
        v += shift;
        shift = v / 36;
        v %= 36;
    
        sb.Append(v < 10 ? (char)('0' + v) : (char) ('A' + v - 10));
      }
    
      if (!added)
        throw new FormatException("Only delimiters. Nothing to add.");
    
      return string.Concat(sb.ToString().Reverse());
    }
    

    让我们看看:

      string[] tests = new string[] {
        "Z006GZYBA1",
        "A9",
        "AZ",
        "1ZZZZZZZZZ",
        "123:456:Abc:zzz", // test with delimiters 
      };
    
      string demo = string.Join(Environment.NewLine, tests
        .Select(test => $"{test,20} => {IncrementString(test)}"));
    
      Console.Write(demo);
    

    结果:

          Z006GZYBA1 => Z006GZYBA2
                  A9 => AA
                  AZ => B0
          1ZZZZZZZZZ => 2000000000
     123:456:Abc:zzz => 123:456:ABD:000
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-08-21
      • 2013-10-09
      • 1970-01-01
      • 2014-10-08
      • 2015-05-03
      • 2014-11-08
      相关资源
      最近更新 更多