그래서 지금까지 내가 찾은 최고의 "해결책"이 있습니다. 그것은 내가 찾고 있던 너바나가 아니지만 각 셀의 형식을 개별적으로 설정하는 것보다 훨씬 빠릅니다.
// 0-based indexes
static string RcToA1(int row, int col)
{
string toRet = "";
int mag = 0;
while(col >= Math.Pow(26, mag+1)){mag++;}
while (mag>0)
{
toRet += System.Convert.ToChar(64 + (byte)Math.Truncate((double)(col/(Math.Pow(26,mag)))));
col -= (int)Math.Truncate((double)Math.Pow(26, mag--));
}
toRet += System.Convert.ToChar(65 + col);
return toRet + (row + 1).ToString();
}
static Random rand = new Random(DateTime.Now.Millisecond);
static string RandomExcelFormat()
{
switch ((int)Math.Round(rand.NextDouble(),0))
{
case 0: return "0.00%";
default: return "0.00";
}
}
struct ExcelFormatSpecifier
{
public object NumberFormat;
public string RangeAddress;
}
static void DoWork()
{
List<ExcelFormatSpecifier> NumberFormatList = new List<ExcelFormatSpecifier>(0);
object[,] rangeData = new object[rows,cols];
for(int r = 0; r < rows; r++)
{
for(int c = 0; c < cols; c++)
{
someVal = r + c;
rangeData[r,c] = someVal.ToString();
NumberFormatList.Add(new ExcelFormatSpecifier
{
NumberFormat = RandomExcelFormat(),
RangeAddress = RcToA1(rowIndex, colIndex)
});
}
}
range.set_Value(MissingValue, rangeData);
int max_format = 50;
foreach (string formatSpecifier in NumberFormatList.Select(p => p.NumberFormat).Distinct())
{
List<string> addresses = NumberFormatList.Where(p => p.NumberFormat == formatSpecifier).Select(p => p.RangeAddress).ToList();
while (addresses.Count > 0)
{
string addressSpecifier = string.Join(",", addresses.Take(max_format).ToArray());
range.get_Range(addressSpecifier, MissingValue).NumberFormat = formatSpecifier;
addresses = addresses.Skip(max_format).ToList();
}
}
}
는 기본적으로 어떤 일이 일어나고 것은 내가 (각 요소는 또한 적용 범위의 A1 스타일 주소를 보유) NumberFormatList의 각 셀의 형식 정보의 목록을 유지하는 것입니다. 원래 아이디어는 워크 시트의 각 고유 한 형식에 대해 Excel.Range를 작성하여 단일 셀에서 해당 범위의 형식을 적용 할 수 있어야한다는 것입니다. 이렇게하면 NumberFormat에 대한 액세스 수가 (잠재적으로) 수천 개에서 몇 개 (사용자가 보유한 다양한 형식)까지 줄일 수 있습니다.
그러나 임의로 긴 셀 목록에서 범위를 구성 할 수 없기 때문에 문제가 발생했습니다. 몇 가지 테스트를 한 결과, 제한이 range.get_Range ("A1, B1, C1, A2, AA5, ....."와 같이) 임의의 범위를 정의하는 데 사용할 수있는 50 ~ 100 개의 셀 사이인지 확인했습니다. 그래서 모든 셀의 목록을 얻은 후에는 한 번에 그 셀을 50 개씩 서식을 적용하는 마지막 while() 루프가 있습니다.
이것은 이상적은 아니지만 그것은 NumberFormat에 대한 액세스 수를 최대 50으로 줄입니다. 중요한 것은 포맷 정보없이 range.set_Value()를 사용하여 스프레드 시트를 작성하는 데 약 3 초가 걸립니다. 시간이 약 10 초로 길어집니다. 각 셀에 형식 정보를 개별적으로 적용하면 스프레드 시트가 작성되는 데 2 분이 걸립니다.
나는 내 자신의 대답을 받아 들였지만, 필자가 결정한 것은 Excel 자동화를 사용하여 파일을 쓰는 것이 나쁜 계획이라는 것입니다. 앞으로 ExcelPackage 라이브러리를 사용하여 직접 작성합니다.xlsx 파일 –
+1 멋진 코드 조각에 대한 하나;) formatSpecifier를 사용하여 셀 범위를 설정할 수 있다는 것을 알지 못했습니다. –