web-dev-qa-db-ja.com

Excelの列文字を数字に変換するアルゴリズムは何ですか?

Excelの列の文字を適切な数字に変換するアルゴリズムが必要です。

これが記述される言語はC#ですが、他の言語でも使用できます。

私はこれをC#に入れようとしているので、オフィスのdllを使いたくないことに注意してください。

「A」の場合、期待される結果は1になります

「AH」= 34の​​場合

「XFD」= 16384の場合

58
David Basarab
public static int ExcelColumnNameToNumber(string columnName)
{
    if (string.IsNullOrEmpty(columnName)) throw new ArgumentNullException("columnName");

    columnName = columnName.ToUpperInvariant();

    int sum = 0;

    for (int i = 0; i < columnName.Length; i++)
    {
        sum *= 26;
        sum += (columnName[i] - 'A' + 1);
    }

    return sum;
}
107
Ian Nelson
int result = colName.Select((c, i) =>
    ((c - 'A' + 1) * ((int)Math.Pow(26, colName.Length - i - 1)))).Sum();
16
mqp
int col = colName.ToCharArray().Select(c => c - 'A' + 1).
          Reverse().Select((v, i) => v * (int)Math.Pow(26, i)).Sum();
7
wethercotes

文字を最後から最初までループします。各文字の値(A = 1、Z = 26)に26 ** Nを掛けて、合計に加算します。私のC#の文字列操作スキルは存在しないため、非常に複雑な疑似コードを次に示します。

sum=0;
len=length(letters);
for(i=0;i<len;i++)
  sum += ((letters[len-i-1])-'A'+1) * pow(26,i);
5
Sparr

誰かが興味を持っている場合にJavaScriptで作成したソリューションを次に示します。

var letters = "abc".toUpperCase();
var sum = 0;
for(var i = 0; i < letters.length;i++)
{
    sum *= 26;
    sum += (letters.charCodeAt(i) - ("A".charCodeAt(0)-1));
}
alert(sum);
3
Jesse Puente

おそらくそれを基数26の数字のように扱い、基数26の数字を文字に置き換えてください。

したがって、実際には、右端の数字は常に1〜26の間の生の数字になり、「数字」の残り(左側)は26の数が収集されますか?したがって、Aは26の1ロットを表し、Bは2を表します。

例として:

 B = 2 =列2 
 AB = 26 * 1(A) + 2 =列28 
 BB = 26 * 2(B) + 2 =列54 
 DA = 26 * 4(D) + 1 =列105 

3
Chris

私は答えのどれにも満足していないので、ここに短いバージョンがあります:

int col = "Ab".Aggregate(0, (a, c) => a * 26 + c & 31);  // 28

または、A-Za-z以外の文字を無視するには:

int col = " !$Ab$3 ".Aggregate(0, (a, c) => (uint)((c | 32) - 97) > 25 ? a : a * 26 + c & 31); // 28
1
Slai

excel VBAでは、次のように.Rangeメソッドを使用して番号を取得できます。

Dim rng as Range
Dim vSearchCol as variant 'your input column
Set rng.Thisworkbook.worksheets("mySheet").Range(vSearchCol & "1:" & vSearchCol & "1")

次に、.columnプロパティを使用します。

 debug.print rng.column

完全なコードが必要な場合は、以下を参照してください。

Function ColumnbyName(vInput As Variant, Optional bByName As Boolean = True) As Variant
    Dim Rng As Range
    If bByName Then
       If Not VBA.IsNumeric(vInput) Then
            Set Rng = ThisWorkbook.Worksheets("mytab").Range(vInput & "1:" & vInput & "1")
            ColumnbyName = Rng.Column
       Else
            MsgBox "Please enter valid non Numeric column or change paramter bByName to False!"
       End If

    Else
        If VBA.IsNumeric(vInput) Then
            ColumnbyName = VBA.Chr(64 + CInt(vInput))
        Else
            MsgBox "Please enter valid Numeric column or change paramter bByName to True!"
        End If

    End If
End Function
0
V. Wolf

これは本質的に他の回答のいくつかとほぼ同じように機能すると思いますが、数値に相当するアルファで何が起こっているかをもう少し明確にするかもしれません。 0プレースホルダーがないため、これは非常に基数26のシステムではありません。つまり、26番目の列は、ベース26のZの代わりに「A0」または何かになります。また、「アルファgit」は27の累乗を表さないため、ベース27ではありません。バビロニア人がゼロを発明する前に算数があったに違いありません!

  UInt32 sum = 0, gitVal = 1;
  foreach (char alphagit in ColumnName.ToUpperInvariant().ToCharArray().Reverse())
  {
    sum += gitVal * (UInt32)(alphagit - 'A' + 1)
    gitVal *= 26;
  }

他の一部と同様に、文字配列を逆にしたので、指数について何も知る必要はありません。

0
B H