2010-05-02 29 views
6

Có thể tạo và xây dựng một số mã C# dựa trên mã từ cùng một dự án hay không. Tôi đã thử với T4 và Reflection, nhưng có một số vấn đề khóa lắp ráp. Còn cách nào khác không?C# Cách tạo mã từ mã

+0

Tôi có thể hỏi điều gì khiến bạn rời khỏi công cụ nội tâm không? http://www.olegsych.com/2007/12/how-to-use-t4-to-generate-decorator-classes/ –

+0

Có một số vấn đề với giấy phép Microsoft.Cci.dll và FxCop. Nó không được phép sử dụng chúng một cách riêng biệt. Ngoài ra, tôi khá quen thuộc với động cơ T4. – Marko

+1

Kể từ VS 2010 SP1, cần có [không có vấn đề về khóa] (http://blogs.msdn.com/b/garethj/archive/2010/12/11/vs2010-sp1-t4-no-longer-locks-assemblies -in-memory.aspx) khi sử dụng phản chiếu từ T4. – Jon

Trả lời

1

Phản ánh hoạt động tốt cho tôi. Bạn có thể gặp các vấn đề về khóa lắp ráp bằng cách cô lập tác vụ xây dựng của bạn cho một AppDomain riêng biệt trong VS. Khi nhiệm vụ hoàn thành, bất kỳ assembly nào bạn cần sử dụng để tạo mã sẽ được dỡ bỏ cùng với AppDomain của nhiệm vụ. Xem AppDomainIsolatedTask.

+0

Không chắc chắn nếu tôi hiểu. Tôi nên viết nhiệm vụ xây dựng của riêng tôi kế thừa AppDomaniIsolatedTask và khởi động trình tạo mã T4. Là nó? – Marko

+0

Có, bằng cách này bạn sẽ có thể làm việc xung quanh VS khóa hội đồng của bạn trong quá trình xây dựng. Đối với trình tạo mã thực tế, hãy sử dụng những gì phù hợp nhất với bạn - T4 nếu bạn thích T4. –

0

Có biến thể C# .NET của bên thứ ba mà chúng tôi sử dụng tại nơi làm việc.

Cũng là một bài viết thú vị về cách làm một: http://msdn.microsoft.com/en-us/magazine/cc136756.aspx

+1

Có phải anh đang cố gắng xây dựng trình biên dịch hay trình tạo mã không? –

0

Nó thực sự phụ thuộc vào những gì chính xác bạn đang cố gắng để đạt được, nhưng trên một trường hợp chung tôi khuyên bạn nên sử dụng các mẫu T4. Và có, bạn có thể sử dụng các mẫu T4 bên trong dự án của bạn để tạo mã trong dự án của bạn dựa trên một số cài đặt cục bộ, nhưng bạn nên xác định bạn đang cố gắng làm gì.

Nếu bạn muốn tạo mã dựa trên một số lớp mà bạn xác định trong cùng một dự án - điều này nghe có vẻ không dễ dàng (sau khi bạn muốn biên dịch một số lớp trong dự án hiện tại, hãy tạo một số mã dựa trên chúng và sau đó tạo ra các lớp học một lần nữa ... umm ..?)

Nhưng nếu bạn muốn lưu trữ một số cài đặt và sau đó chạy mẫu T4 và tạo một số mã dựa trên các cài đặt này - điều này dễ dàng đạt được. T4MVC là một ví dụ (chúng tạo mã dựa trên tệp cài đặt được sao chép và lưu trữ trong dự án cùng với mẫu T4). Mẫu này cũng xem xét các tệp hiện có sẵn trong giải pháp và tạo các hằng số chuỗi dựa trên từng tệp. Đó là loại âm thanh như nó sẽ thực sự giúp bạn với vấn đề của bạn, bất cứ điều gì là :)

Nếu bạn vẫn không chắc chắn - bạn có thể chỉ định thêm chi tiết về những gì bạn muốn làm, và chúng tôi sẽ cố gắng giúp bạn :)

+0

Cảm ơn câu trả lời. Những gì tôi đang cố gắng đạt được là có thể tạo thêm mã dựa trên các lớp trong dự án của tôi. Một cái gì đó như CloneEntity(), SerializeEntity() hoặc InvokeSomeMethod. Tất cả mã này phụ thuộc vào tên lớp, thành viên ... Mã được tạo có thể nằm trong một dự án khác, nhưng sẽ tốt hơn nếu giữ mọi thứ lại với nhau. – Marko

+0

Tôi hiểu .. Bạn có thể sẽ phải giữ các lớp này trong một dự án riêng biệt, vì bạn đang cố gắng tạo mã trên các thực thể bán được tạo ra và tôi không chắc chắn liệu điều đó có thể xảy ra hay không. Có vẻ như bạn thực hiện chính xác phương pháp mà bạn đang sử dụng, nhưng hãy giữ các T4 này trong một hội đồng riêng biệt - nó chỉ hoạt động (nó không phải là một hội đồng riêng biệt với JUST T4 của khóa học .. Bạn có thể có bất kỳ các loại công cụ trong đó, nhưng T4 nên phản ánh các lớp học trong một hội đồng riêng biệt, đã được biên soạn :)) Chúc may mắn! –

1

Bạn chắc chắn có thể viết trình tạo mã của riêng mình, tất cả trong C# - sau khi tất cả, "mã" đang được tạo ra chỉ là một tệp văn bản bạn viết ra.

Nhưng có vấn đề gì với mẫu T4? Họ cung cấp rất nhiều chức năng mà bạn không phải tái tạo lại một lần nữa - tại sao không sử dụng nó? Bạn có thể cho chúng tôi biết chi tiết hơn về những vấn đề bạn đang gặp phải với T4 không?

T4 thực sự chỉ là một loạt các lớp trong .NET. Vì vậy, bạn có thể viết trình tạo mã của riêng bạn xử lý một số logic và sử dụng T4 để làm việc thay thế các phần giá trị mẫu đó. Nhưng một lần nữa: để giúp bạn chẩn đoán vấn đề T4 của mình, chúng tôi cần biết thêm về những vấn đề đó ...

+0

Ví dụ tôi muốn tạo ra một CloneEntity cho mô hình L2S của tôi. Tôi cần đọc các thuộc tính và tạo phương thức Clone. Nó có thể được thực hiện với T4 và sự phản chiếu, nhưng có vấn đề về khóa lắp ráp. Bạn phải đóng VS và mở lại sau mỗi lần chạy. – Marko

+1

Đối với CloneEntity: tại sao không chỉ serialize thực thể vào một dòng bộ nhớ và deserialize nó từ đó? Đó là cách tiêu chuẩn để thực hiện nó, nó đã chứng minh được giá trị của nó, nó không đòi hỏi bất kỳ sự lừa đảo hoặc tạo mã nào. –

1

This example from Oleg Sych sử dụng công cụ nội suy của FXCop thay vì phản ánh. Bằng cách đó, các hội đồng không bị khóa.

Thật không may, Reflection được tối ưu hóa để thực thi mã. Một giới hạn cụ thể làm cho nó không phù hợp cho việc tạo mã - lắp ráp được tải bằng cách sử dụng Phản chiếu chỉ có thể được tải xuống với AppDomain của nó. Vì các mẫu T4 được biên dịch thành.NET hội đồng và được lưu trữ để cải thiện hiệu suất của việc tạo mã , sử dụng Phản ánh để truy cập vào cấu phần làm T4 khóa nó.

Hoặc, nếu bạn chỉ nhắm mục tiêu các lớp LINQ to SQL, bạn có thể tạo mã từ tệp dbml thay vì mã mà L2S tạo từ dbml. I've got an example of something similar (an edmx file) on my own blog.