本文介绍了以编程方式检索Excel库的版本的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

有没有办法编程检索C#中使用的Excel Interop库的版本?



我知道我可能会在注册表中查找安装的Microsoft Office实例,但如果Excel库包含此信息,我很好奇。



当我引用库时,我知道这个信息包含在Visual Studio中,但是在运行时我看不到这些信息。



我问这个是因为它在保存工作簿时指定文件扩展名,并且如果使用'.xls'保存了2007工作簿,则2007会向扩展名指出

解决方案

简单的答案是这样的:你不需要知道加载哪个PIA版本来解决你的问题。你想知道的是哪个版本的Excel正在运行。虽然运行的Excel版本和PIA版本通常相同,但不一定是,在这种情况下,它是您关心的Excel版本,而不是PIA版本。 / p>

确定哪个Excel版本正在运行并不困难,但它不是那么容易,因为它应该是因为>



为了解决你的问题,我可以建议采取两种可能的行动方案之一:



(1)尝试我以上给出的代码来确定正在运行的Excel版本。如果你这样做,并相应地调整你的代码,它将工作,我保证。如果它失败,显示你的代码,我确定我们可以让它工作。



(2)不要在你给的工作簿名称中指定扩展名它。让Excel应用程序为您添加默认扩展名。你是正确的,如果你在Excel 2007中保存时指定一个.xls扩展名,它将会遵守这个扩展名,而不是工作簿版本。然而,最简单的是在保存工作簿时省略扩展名,Excel应用程序会自动将.xls或.xlsx附加到工作簿名称,具体取决于当前正在运行的Excel版本:

  Excel.Application excelApp = new Excel.Application(); 
Excel.Workbook工作簿= excelApp.Workbooks.Add(Type.Missing);

workbook.SaveAs(
MyWorkbook,Type.Missing,Type.Missing,Type.Missing,Type.Missing,Type.Missing,
Excel.XlSaveAsAccessMode.xlNoChange, Type.Missing,Type.Missing,Type.Missing,
Type.Missing,Type.Missing);

上面的结果是一个名为MyWorkbook.xls或MyWorkbook.xlsx的工作簿,具体取决于运行的是哪个版本的Excel。简而言之,让Excel为您做的工作,以便您不用担心。


Is there a way to programatically retrieve the version of the Excel Interop Libraries being utilized with C#?

I know I could probably look in the registry to figure out the installed instance of Microsoft Office, but I was curious if the Excel Libraries contain this information.

I know this information is contained in Visual Studio when you reference the library, but I can't see that information at runtime.

I am asking this because it dictates the file extension when you save the workbook, and if you save a 2007 workbook with '.xls', 2007 complains about the extension being incorrect.

解决方案

The short answer is this: you do not need to know which PIA version is loaded to solve your problem. What you want to know is which version of Excel is actually running. Although the running Excel version and the PIA version are usually the same, they do not have to be, and, in this case, it is the Excel version that you care about, not the PIA version.

Determining which Excel version is running is not hard, but it is not quite as easy as it should be because the Excel.Application.Version property can return strings such as "11.0" or "9.0a" or the like, so one cannot necessarily directly parse it into an integer value. You can rely on the fact that everything to the left of the decimal point (".") is the version number, however, so the following code works for all versions:

Excel.Application excelApp = new Excel.Application();

string versionName = excelApp.Version;
int length = versionName.IndexOf('.');
versionName = versionName.Substring(0, length);

// int.parse needs to be done using US Culture.
int versionNumber = int.Parse(versionName, CultureInfo.GetCultureInfo("en-US"));

if (versionNumber >= 12)
{
    // Excel 2007 or above.
}
else
{
    // Excel 2003 or below.
}

As for the PIA vs. Excel object model issue, which Primary Interop Assembly (PIA) your assembly references when developing versus which PIA is actually loaded at runtime on the target machine can be different. For example, if you reference the Excel 2002 PIAs and the target machine is using Excel 2007, then (generally) the Excel 2007 PIAs will get loaded. The rule is that the highest-versioned Office PIA available on the target machine gets loaded at runtime.

It gets even more complicated in that it is possible (although, definitely not likely) for the target machine to have, say, Excel 2007 loaded on the target machine, but the highest-available PIAs be for Excel 2003. In this case, Excel 2007 would load, but your code would be working against the Excel 2003 PIAs. The reverse can occur as well: the Excel 2007 PIAs are available, but the highest actual version installed on the machine is Excel 2003 -- in this case Excel 2003 will load, but your code will be working against the Excel 2007 PIAs.

These scenarios are very unlikely in a standard setup. It is most likely to occur on a developer's machine where either (1) more than one Excel version is present on the machine at the same time, or (2) Excel versions have been added and removed, but the PIAs not removed with it (which, in itself, is also unlikely, as I believe the PIAs are uninstalled automatically, but I could be wrong about this).

For more on this, see Andrew Whitechapel's article Why is VS development not supported with multiple versions of Office?

While all these scenarios sound a bit scary, the interfaces in Excel's object model are extremely consistent and therefore are nearly 100% backward-compatible. In general, if you bind to a given Excel PIA version, then your code will run successfully against that version of Excel or higher, pretty much regardless of the scenio involved. There are a few quirks though, as you have discovered, but the key is to know which Excel version is actually running. Knowing which PIA is running is not generally important -- as long as the PIA version you developed against (or higher) is available, then the PIA itself should not cause any issues.

Edit: Follow up to phsr's comment:

I know that it might "feel like" it is the PIA that is the issue, but it is Excel object model that is actually loaded that matters here, not the PIA. In addition, there is a 99.9% chance that the Excel application version number is the SAME as the PIA version. It is extremely rare that they would differ. And where they do differ, it would be the Excel version that matters, not the PIA (so long as the PIA is the same version as the PIA you developed against, or higher).

To try to clarify this, the PIAs only specify the interfaces involved, not the functionality. The Excel 2003 SaveAs method has exactly the same parameter signature as the Excel 2007 SaveAs method, so the PIAs do not differ here. How the SaveAs method is executed, however, depends on which version of the Excel object model is actually running.

To fix your problem, I can suggest taking one of two possible courses of action:

(1) Try the code I gave above to determine the Excel version that is running. If you do this and adjust your code accordingly it will work, I promise. If it fails, show your code and I'm sure we can get it to work.

(2) Don't specify the extension in the workbook name that you give it. Let the Excel application add the default extension for you. You are correct in that if you specify a ".xls" extension when saving in Excel 2007, it will respect that extension, but not the workbook version. Easiest here, however, is to simply omit the extension when saving your workbook and the Excel application will automatically append ".xls" or ".xlsx" to the workbook name, depending on which Excel version is currently running:

Excel.Application excelApp = new Excel.Application();
Excel.Workbook workbook = excelApp.Workbooks.Add(Type.Missing);

workbook.SaveAs(
    "MyWorkbook", Type.Missing, Type.Missing, Type.Missing, Type.Missing, Type.Missing,
     Excel.XlSaveAsAccessMode.xlNoChange, Type.Missing, Type.Missing, Type.Missing,
     Type.Missing, Type.Missing);

The result of the above is a workbook named either "MyWorkbook.xls" or "MyWorkbook.xlsx", depending on which version of Excel is running. In short, let Excel do the work for you so that you don't have to worry about it.

这篇关于以编程方式检索Excel库的版本的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-24 18:08
查看更多