Импортировать пространства имен в CodeSnippetCompileUnit

При использовании CodeCompileUnit для генерации кода через CodeDOM вы можете импортировать пространства имен, создав пространство имен CodeNamespace отдельно от пространства имен, в котором вы определяете свой тип (ы). Использование свойства Imports позволяет добавлять желаемые пространства имен. Если вы добавите CodeNamespace в модуль CodeCompile, импортированные файлы появятся в верхней части файла, созданного CodeDOM.

Например, используя CSharpCodeProvider для компиляции следующего графа CodeDOM:

CodeCompileUnit compileUnit = new CodeCompileUnit();
CodeNamespace importsNamespace = new CodeNamespace {Imports = {new CodeNamespaceImport("System"), new CodeNamespaceImport("System.Collections.Generic"), new CodeNamespaceImport("System.Linq")}};
CodeNamespace typeNamespace = new CodeNamespace("MyTypeNamespace");
compileUnit.Namespaces.Add(importsNamespace);
compileUnit.Namespaces.Add(typeNamespace);

будет генерировать

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a tool.
//     Runtime Version:4.0.30319.269
//
//     Changes to this file may cause incorrect behavior and will be lost if
//     the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

using System;
using System.Collections.Generic;
using System.Linq;

namespace MyTypeNamespace {

}

CodeSnippetCompileUnit позволяет вам компилировать определения типов, которые были введены в виде строки. Например, строка «общедоступный класс TestClass {}» может использоваться в качестве значения для CodeSnippetCompileUnit. Используя тот же код, что и выше, с CodeSnippetCompileUnit:

const string testClassCodeString = "public class TestClass {}";
CodeSnippetCompileUnit snippetCompileUnit = new CodeSnippetCompileUnit {Value = testClassCodeString};
CodeNamespace importsNamespace = new CodeNamespace {Imports = {new CodeNamespaceImport("System"), new CodeNamespaceImport("System.Collections.Generic"), new CodeNamespaceImport("System.Linq")}};
CodeNamespace typeNamespace = new CodeNamespace("MyTypeNamespace");
compileUnit.Namespaces.Add(importsNamespace);
compileUnit.Namespaces.Add(typeNamespace);

сгенерирует файл, содержащий только:

public class TestClass {}

Как вы можете заключить этот тип в пространство имен или импортировать пространства имен в файл, созданный из CodeSnippetCompileUnit?


person bozalina    schedule 18.07.2012    source источник


Ответы (1)


Несмотря на то, что CodeSnippetCompileUnit является производным от CodeCompileUnit, компилятор игнорирует свойство Namespaces при генерации кода из графа CodeDOM. Код, созданный из CodeSnippetCompileUnit, содержит только строку, которая находится в свойстве Value объекта.

Если у вас есть фрагмент кода без контекста, единственный вариант для импорта пространств имен или включения фрагмента в пространство имен - это изменить строку перед установкой значения CodeSnippetCompileUnit.

Пример использования кода из вопроса выше в качестве отправной точки:

string namespaceString = "MyTypeNamespace";
string codeString = "public class TestClass {}";
string snippetValue = string.Format(@"
using System;
using System.Collections.Generic;
using System.Linq;

namespace {0}
{{

{1}

}}", namespaceString, codeString, Environment.NewLine);

var snippetCompileUnit = new CodeSnippetCompileUnit {Value = snippetValue};

Это сгенерирует:

using System;
using System.Collections.Generic;
using System.Linq;

namespace MyTypeNamespace
{

public class TestClass {}

}
person bozalina    schedule 18.07.2012
comment
Вы уже используете дословную строку, поэтому я думаю, что фактическая новая строка будет лучше, чем ваш {2}. - person svick; 19.07.2012
comment
Вы совершенно правы. В этом случае это, вероятно, улучшает читаемость образца кода. Обновлено по вашему предложению. - person bozalina; 19.07.2012