2009-08-04 43 views
31

Tôi đang tìm cách tăng tốc tác vụ lặp lại khi viết mã. Tôi có ReSharper và tôi đang nghĩ rằng một tùy biến có thể làm những gì tôi cần.ReSharper có thể tạo mã sao chép các thuộc tính từ một đối tượng này sang đối tượng khác không?

Tôi có hai đối tượng cùng loại. Tôi muốn sao chép tất cả các thuộc tính công cộng của một đối tượng cho đối tượng khác. Tôi muốn công cụ, ReSharper trong trường hợp này, để tạo mã cho tôi. Tôi sẽ cho nó biết tên của đối tượng đầu tiên và đối tượng thứ hai. Tôi muốn nó tìm tất cả các thuộc tính công khai của đối tượng đầu tiên và sao chép các giá trị cho đối tượng thứ hai.

Dưới đây là các loại mã Tôi đang tìm kiếm để có được tạo ra với một công cụ như ReSharper:

foo.Name = moo.Name; 
foo.Age = moo.Age; 
foo.City = moo.City; 

Tự động mã đơn giản này cho phép sao chép các giá trị từ phải sang trái sẽ tiết kiệm rất nhiều thời gian và tôi nghĩ rằng ReSharper có thể làm được. Tuy nhiên, tôi đã không nhìn thấy bất cứ điều gì bật lên trong tìm kiếm cho nó mặc dù.

Tôi không tìm kiếm kỹ thuật tạo mã CodeSmith hoặc mẫu T4 vì tôi chỉ muốn tạo các dòng cụ thể này trong lớp của mình, không tạo và toàn bộ lớp hoặc tệp riêng biệt.

Có ai biết cách nhấn một vài lần nhấn phím, nhập tên đối tượng "foo" và "moo" ở trên và có công cụ tạo bản sao này từ dòng mã phải sang trái không?

Cập nhật:

Tôi đã tìm thấy một số tài liệu về xây dựng mở rộng để ReSharper, và điều này có lẽ có thể đạt được bởi con đường đó, nhưng nó trông thực sự có liên quan.

http://www.jetbrains.net/confluence/display/ReSharper/PowerToys+Pack+3.0+User+Guide

này đang bắt đầu trông giống như một thử thách cuối tuần trừ khi ai đó đã viết nó.

Trả lời

8

Tôi không tin Resharper có thể thực hiện việc này, nhưng nguồn mở AutoMapper có thể. Bạn mới sử dụng AutoMapper? Hãy xem trang Getting Started.

+0

tôi chưa bao giờ nghe nói về công cụ này. Với các lớp truy cập dữ liệu và các hợp đồng dữ liệu làm cho loại mã này là cần thiết, đây là một công cụ tuyệt vời! – Vaccano

+2

Automapper chắc chắn là một điều tuyệt vời cho một số trường hợp, nhưng có thể rất chậm đối với số lượng lớn các đối tượng. – Telavian

+7

Chúng tôi đã sử dụng Automapper trong một ứng dụng doanh nghiệp lớn với hàng tấn DTO và sau 6 tháng, chúng tôi đã từ bỏ nó vì khó duy trì và gỡ lỗi hơn việc gán đồng bằng cũ của các thuộc tính. Không nên được coi là một hit lớn chống lại AM nhưng cuối cùng chúng tôi chỉ muốn phá vỡ trên một dòng mã thay vì đọc ra một thông báo lỗi lớn (Thông báo lỗi là chính xác và hữu ích). – TheDev6

-2

Đơn giản chỉ cần sao chép các giá trị từ bên này sang bên kia là khá xấu.

Bạn có thể thấy nó tốt hơn để tạo một phương pháp để đưa vào các lớp học sử dụng sự phản chiếu để sao chép các thuộc tính công cộng. Bạn có thể lưu phương thức này để chia sẻ lại thành các lớp khác mà bạn cần chức năng này.

1

Đây là một lớp đơn giản để sao chép một đối tượng. Nó không chính xác những gì bạn yêu cầu nhưng có lẽ điều này sẽ hữu ích cho bạn:

//.Net 2.0 
using System; 
using System.Collections.Generic; 
using System.IO; 
using System.Runtime.Serialization.Formatters.Binary; 
using System.Text; 

namespace YourNameSpace { 
    public static class ObjectCloner { 
     public static T Clone<T>(T obj) { 
     using (MemoryStream buffer = new MemoryStream()) { 
      BinaryFormatter formatter = new BinaryFormatter(); 
      formatter.Serialize(buffer, obj); 
      buffer.Position = 0; 
      T temp = (T)formatter.Deserialize(buffer); 
      return temp; 
     } 
     } 
    } 
} 
-1

Đây là loại điều mà Cog tỏa sáng. Về cơ bản, Cog là công cụ tạo mã. Mã được tạo ra thông qua Python.

+6

Vì vậy, đề xuất câu trả lời cho câu hỏi của tôi là sử dụng chương trình Python để giúp tôi viết mã C# của mình? Bạn có một ví dụ về điều này? – a7drew

4

Tôi đồng ý với @Ben Griswold.
Trong hầu hết các trường hợp, Automapper là con đường để đi.

Nhưng khi bạn thực sự muốn tạo ra mã mà bản tính từ một đối tượng khác, hãy thử này:

  1. Tạo một lớp mới và xuất phát từ lớp từ mà bạn muốn sao chép thuộc tính.
  2. Nhấp chuột phải vào lớp dẫn xuất mới này và nhấp vào 'Trình kết xuất lại> Giao diện trích xuất'.
  3. Kiểm tra tất cả các thuộc tính mà bạn muốn sao chép.
  4. Chọn 'Đặt bên cạnh' vì giao diện này sẽ chỉ là tạm thời.
  5. Nhấp vào 'Tiếp theo'.
  6. Sửa đổi lớp dẫn xuất của bạn để bạn không còn kế thừa từ lớp cơ sở nữa và bạn chỉ đang triển khai giao diện mới của mình. Mong đợi để nhìn thấy một squiggle đỏ.
  7. Đặt con trỏ lên hình vuông màu đỏ và nhấn 'ALT-ENTER' để 'Triển khai thành viên'.
  8. Nhấp vào 'Hoàn tất'.
  9. Xóa giao diện tạm thời đó và sửa đổi lớp học của bạn để bạn không còn triển khai nó nữa.
43

Thật dễ dàng. ReSharper không làm điều đó, nhưng bạn có thể sử dụng một REGEX siêu duper!

Trong Visual Studio:

public string Email { get; set; } 
    public string CellPhone { get; set; } 
    public int NumChildren { get; set; } 
    public DateTime BirthDate { get; set; } 
  1. Chọn tất cả tài sản của bạn. Nhấn CTRL-D để sao chép.

  2. Bây giờ, hãy nhấn CTRL-H để thay thế. Đảm bảo rằng .* được chọn để đối sánh Regex.

  3. Thay thế: public [\w?]* (\w*) .* (Regex này có thể cần phải được tinh chỉnh)

  4. Với: dest.$1 = source.$1;

Bây giờ bạn có một số mã đẹp bạn có thể đặt trong một phương pháp lựa chọn của bạn:

dest.Email = source.Email; 
    dest.CellPhone = source.CellPhone; 
    dest.NumChildren = source.NumChildren; 
    dest.BirthDate = source.BirthDate; 
+0

Cho phép tôi cũng cắm * AutoMapper *. Nó thực sự khá dễ dàng để sao chép các thuộc tính với nó. Nó phụ thuộc vào tình hình của bạn tất nhiên. – Jess

8

Điều này phần nào dẫn xuất từ ​​câu trả lời của @Jess (regex của anh ấy không hoạt động cho tôi trên VS2013) nhưng thay vì sử dụng Visual Studio Tôi là using regex101

Nhấp vào liên kết ở trên và chỉ dán thuộc tính của bạn vào trường Test string và bạn sẽ được ánh xạ.

Regex tôi đã sử dụng

public [A-Za-z\?]* ([A-Za-z0-9]*) .*

và thay thế

Dest.$1 = Source.$1

niềm hy vọng này giúp bạn tiết kiệm một chút thời gian.

+0

Xin chào Matas. Có, tôi cho phép cho các loại nullable và đã phá vỡ regex trong câu trả lời của tôi. Bây giờ nó đã được sửa. Cảm ơn. – Jess

1

Dựa trên câu trả lời @Matas Tôi đã tạo một phiên bản mạnh mẽ hơn using regex101 bỏ qua generics, thuộc tính và nhận xét và bình thường hóa không gian.

Regex: *((\/+.*\n*.*)|(\[.*\]\n*.*))*public [A-Za-z\_\?\<\>]* ([A-Za-z0-9\_]*) .*(\n|)*

Thay thế: $4 = person.$4,\n

Các vấn đề liên quan