【问题标题】:Array has string value, I want an integer数组有字符串值,我想要一个整数
【发布时间】:2014-10-10 03:16:59
【问题描述】:

我是 C# 编程新手,我从以下方面学到了几乎所有信息: http://unity3d.com/learn/tutorials/modules/beginner/scripting,youtube,这个网站,还有很多通过google找到的编程教程网站。

在我在 Unity 中的单一行为代码中,我最终试图制作一个以 12 为基数的计算器。 为此,我需要 12 个数字,我写了一个字符串数组来表示它们:

private string[] numerals = {"0","1","2","3","4","5","6","7","8","9","X","E"};
public string thisNum;

我的 Start 和 calcNum 函数:

void Start ()
{
    thisNum = numerals[10];
    calcNum ();
}
void calcNum ()
{
    print(thisNum);
}

太好了,我可以输入:print (thisNum);,然后返回X

但是,我如何获得:print (thisNum + thisNum) 以返回 18

我知道它不是整数,因此它不能将 2 个字符串相加得到总和,而是得到:XX

那么,我如何将 X 表示为这么多:

o o o, o o o, o o o, o

而不仅仅是字母 X。我现在重置了这个项目大约 6 次。

我一直在考虑 for 循环或 if (X) than 10,但是,我最终总是使用以 10 为底的数字来表示数字,这有点蹩脚。

我只需要一点点推动就可以朝着正确的方向前进,非常感谢您的帮助,

谢谢。

【问题讨论】:

  • 根据基数 12,X + X = 16 而不是 18。
  • 0 1 2 3 4 5 6 7 8 9 X --- E 10 11 12 13 14 15 16 17 18 ---X + X = 18 我很确定。
  • 给定一个整数,反复除以 12。余数是以 12 为底的数字。将每个数字转换为其字符表示,并以正确的顺序连接字符。
  • 等等,我好像看到有人说“int index = Array.IndexOf(numerals, "some string");” monodevelop 不知道数组是什么意思……它提供了 arrayList 作为选项。
  • 我不确定我是否遵循,“重复除以 12”是什么意思,我怎么知道这样做多少次?

标签: c# arrays algorithm math base


【解决方案1】:

这可能会有所帮助。

从字符数组而不是字符串开始。

var numerals = new []
{
    '0', '1', '2', '3', '4', '5',
    '6', '7', '8', '9', 'X', 'E',
};

创建几个字典以返回每个数字的基数为 10 的值并执行反向查找。

var nis =
    numerals
        .Select((n, i) => new { n, i })
        .ToArray();

var n2i = nis.ToDictionary(_ => _.n, _ => _.i);
var i2n = nis.ToDictionary(_ => _.i, _ => _.n);

然后,要在 base 10 和 base 12 之间进行转换,您需要几个辅助函数。

Func<int, IEnumerable<char>> getReversedNumerals = null;
getReversedNumerals = n =>
{
    IEnumerable<char> results =
        new [] { i2n[n % 12], };
    var n2 = n / 12;
    if (n2 > 0)
    {
        results = results.Concat(getReversedNumerals(n2));
    }
    return results;
};

Func<IEnumerable<char>, int, int> processReversedNumerals = null;
processReversedNumerals = (cs, x) =>
    cs.Any()
        ? x * n2i[cs.First()]
            + processReversedNumerals(cs.Skip(1), x * 12)
        : 0;

现在您可以根据助手定义转换函数。

Func<int, string> convertToBase12 =
    n => new String(getReversedNumerals(n).Reverse().ToArray());

Func<string, int> convertToBase10 =
    t => processReversedNumerals(t.ToCharArray().Reverse(), 1);

最后你可以执行转换:

var b10 = convertToBase10("3EX2"); //6890
var b12 = convertToBase12(6890); //3EX2

【讨论】:

  • 感谢您的贡献!我要研究这个。虽然我使用的是 C#,但这可能很有用。谢谢!
  • @BuffooneryAccord - 它是 c#。
  • 哎呀,是的,我的错,我看到所有那些 和 vars,看起来像 Javascript。我从不使用 Javascript,而且我对编程很陌生。现在我正在查看它们,非常复杂,但我相信我会理解每个部分。
【解决方案2】:

这取决于您如何获取和存储这些值。

假设您将它们存储为以 12 为基数的字符串,您需要在它表示的整数 base10 值和您用来表示它的字符串值之间来回转换方法。

public String Base12Value(int base10)
{
    String retVal = "";
    while (base10 > 0)
    {
        //Grab the mod of the value, store the remainder as we build up.
        retVal = (base10 % 12).ToString() + retVal;

        //remove the remainder, divide by 12
        base10 = (base10 - (base10 % 12)/12);
    }

    return retVal;
}

public int Base10Value(String base12)
{
    int retVal = 0;
    for (int i = 1; i <= base12.Length; i++)
    {
        int tmpVal = 0;
        char chr = base12[base12.Length-i];
        //Grab out the special chars;
        if (chr == 'X')
        {
            tmpVal = 10;
        } else if (chr == 'E')
        {
            tmpVal = 11;
        }
        else
        {
            tmpVal = int.Parse(chr.ToString());
        }

        //Times it by the location base.
        retVal += tmpVal * (10 ^ (i - 1));

    }
    return retVal;
}

这样你就可以做类似的事情了

print(Base12Value(Base10Value(thisNum) + Base10Value(thisNum)));

这有点笨拙,但可以完成工作。

【讨论】:

  • 天哪,所有这些答案都在这么短的时间内完成。谢谢!
【解决方案3】:

哦,虽然有些人已经提出了,但这是我的,因为我一直在努力。

using System;
using System.Text;
using System.Collections.Generic;

public class Base12 
{
    public static void Main()
    {
        Base12 X = new Base12(10);
        Base12 X2 = new Base12(10);
        Base12 XX = X + X2;
        Console.WriteLine(XX); // outputs 18
    }

    public int DecimalValue { get; set; }

    public readonly char[] Notation = new char[] {'0', '1' , '2' , '3', '4', '5' , '6', '7', '8', '9', 'X', 'E'};

    public Base12(int x)
    {   
        DecimalValue = x;
    }

    public override string ToString()
    {
        List<char> base12string = new List<char>();
        int copy = DecimalValue;
        while(copy > 0)
        {
            int result = copy % 12;
            base12string.Add(Notation[result]);
            copy = copy / 12;
        }

        StringBuilder str = new StringBuilder();
        for(int i = base12string.Count - 1; i >= 0; i--)
        {
            str.Append(base12string[i]);
        }
        return str.ToString();
    }

    public static Base12 operator+(Base12 x,  Base12 y)
    {
        return new Base12(x.DecimalValue + y.DecimalValue);
    }

    // Overload other operators at your wish
}

【讨论】:

    【解决方案4】:

    这是我对您的问题的实现。我不得不说,这是一个有趣的项目! 我不想使用任何十进制值,因为我认为那是作弊。我只使用小数作为列表的索引。

    using System;
    using System.Collections.Generic;
    using System.Linq;
    
    class Base12
    {
        static IList<char> values = new List<char>{ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'X', 'E' };
    
        public string Value { get; set; }
    
        public Base12(string value)
        {
            this.Value = value;
        }
    
        public static Base12 operator +(Base12 x, Base12 y)
        {
            var xparts = x.Value.ToArray();
            var yparts = y.Value.ToArray();
    
            int remember = 0;
            string result = string.Empty;
    
            for (int i = 0; i < Math.Max(yparts.Length, xparts.Length) ;i++)
            {
                int index = remember;
                if (i < xparts.Length)
                {
                    index += values.IndexOf(xparts[xparts.Length - i - 1]);
                }
                if (i < yparts.Length)
                {
                    index += values.IndexOf(yparts[yparts.Length - i - 1]);
                }
    
                if (index > 11)
                {
                    index -= 12;
                    remember = 1;
                }
                else
                {
                    remember = 0;
                }
    
                result = values[index] + result;
            }
    
            if (remember > 0)
            {
                result = values[remember] + result;
            }
    
            return new Base12(result);
        }
    
        public static implicit operator Base12(string x)
        {
            return new Base12(x);
        }
    
        public override string ToString()
        {
            return this.Value;
        }
    }
    

    下面是你可以如何使用它:

    Base12 x = "X";
    Base12 y = "X";
    Base12 z = x + y;
    Debug.Print(z.ToString());
    // returns 18
    
    Base12 x = "X12X";
    Base12 y = "X3";
    Base12 z = x + y;
    Debug.Print(z.ToString());
    // returns X211
    

    【讨论】:

      猜你喜欢
      • 2013-11-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多