1

I'm new to programming C#, and I've learned almost all of my information from: http://unity3d.com/learn/tutorials/modules/beginner/scripting, youtube, this site, and many programming tutorial sites found through google.

In my monobehavior code within Unity, I am ultimately trying to make a base 12 calculator. To do so, I need 12 numerals, I wrote a string array to represent them:

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

my Start and calcNum functions:

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

This is great, I can type: print (thisNum);, and get back X.

But, how do I get: print (thisNum + thisNum) to return 18?

I know it's not an integer, therefore it can not add 2 strings to get a sum, you instead get: XX.

So then, how do I represent X as this many:

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

and not just the letter X. I reset this project about 6 times now.

I was thinking of for-loops or if (X) than 10, but, I always end up using base 10 to represent numbers, which is kind of lame.

I just need a little push to get going in the right direction, and would really appreciate the help,

thank you.

JoriO
  • 1,050
  • 6
  • 13

4 Answers4

1

This might help.

Start with an array of characters rather than strings.

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

Create a couple of dictionaries to return the base 10 value of each numerals and to perform the reverse look-up.

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

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

Then to convert between base 10 and base 12 you need a couple of helper functions.

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;

Now you can define the conversion functions in terms of the helpers.

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

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

And finally you can perform conversions:

var b10 = convertToBase10("3EX2"); //6890
var b12 = convertToBase12(6890); //3EX2
Enigmativity
  • 113,464
  • 11
  • 89
  • 172
  • Thanks for your contribution! I'm going to study this. Although I am using C#, this could be useful. thanks! – BuffooneryAccord Oct 10 '14 at 04:55
  • @BuffooneryAccord - It is c#. – Enigmativity Oct 10 '14 at 05:03
  • oops, yea, my bad, I was seeing all those <, >, and vars, looked like Javascript. I never use Javascript, plus I'm really new to programming in general. Right now I'm looking at them all, quite complex, but I'm sure I'll understand each part. – BuffooneryAccord Oct 10 '14 at 05:11
0

It depends on how you're taking in, and storing the values.

Assuming you're storing them as their base 12 string, you'll need conversion methods back and forth between the integer base10 value it represents, and the string value that you're using to represent it.

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;
}

So you can then do things like

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

which is a tad clunky, but gets the job done.

Andrew Alderson
  • 893
  • 12
  • 18
0

Oh, even though some already put it, here is mine since I worked on it.

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
}
Ghasan غسان
  • 5,577
  • 4
  • 33
  • 44
0

Here's my implementation of your problem. I have to say, this is one fun project! I didnt want to use any decimal values, because I thought that was cheating. I only used decimals as de index for the list.

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;
    }
}

And here is how you might use it:

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
Jesse de Wit
  • 3,867
  • 1
  • 20
  • 41