2012-12-18 24 views
5

Có rất nhiều câu hỏi về việc mã hóa một hệ thống huy hiệu tương tự như SO, câu hỏi của tôi là khác nhau. Giả sử tôi có hệ thống trang web, huy hiệu/thành tích, được lưu trữ trong DB dưới dạng hàng có khóa thành tích (id), id người dùng và bất kỳ dữ liệu nào khác.Kiến trúc cho các thành tích/huy hiệu

Câu hỏi đơn giản của tôi là, tôi nên lưu trữ ID huy hiệu ở đâu? Tôi có một lớp cho mỗi thành tích với tất cả các dữ liệu và phương pháp để thử nghiệm nếu nó đã kiếm được. Tôi tưởng tượng tôi có thể có hàng chục hoặc hàng trăm tại một số điểm. Tôi muốn các ID được sử dụng mã hóa cứng chỉ một lần, và ở một nơi ngắn gọn, vì vậy tôi không có cơ hội vô tình thay đổi chúng hoặc trộn chúng lên.

tôi khó có thể mã hóa chúng trong lớp, như

public int Key { get { return 15; } } // I'm calling it Key, not ID 

nhưng nếu tôi chia thành tựu của tôi trong nhiều file Tôi không muốn phải chạy quanh tìm kiếm Key cao nhất khi tôi thêm một mới một và mạo hiểm một sai lầm.

tôi có thể đặt chúng trong một số từ điển trong lớp khác ...

public class AchievementSet 
{ 
    private Dictionary<int, Achievement> _achievements; 

    public AchievementSet() 
    { 
     _achievements = new Dictionary<int, Achievement>() 
     { 
      { 1, new SomethingAchievement() } 
     }; 
    } 
} 

Nhưng bây giờ lớp mình không biết chìa khóa riêng của nó, và nó cần phải (hoặc hiện nó?) Nếu tôi thông qua nó vào các nhà xây dựng bây giờ tôi có nguy cơ không khớp các con số.

Bất kỳ đề xuất nào?

+1

Tại sao bạn không lưu các huy hiệu trong cơ sở dữ liệu? –

+1

Tôi cho rằng, vì có mã được liên kết với mỗi huy hiệu và bạn vẫn cần phải khớp với đoạn mã đó với ID huy hiệu. Vì vậy, về cơ bản nó sẽ không giải quyết bất cứ điều gì. – guillaume31

Trả lời

2

Trong bối cảnh Stack Overflow, tôi tưởng tượng mỗi huy hiệu có các tính chất như: Id, Tên, Class (Bronze, bạc hoặc vàng) và mô tả, vv

Bạn đề cập rằng bạn đang có một lớp cho mỗi huy hiệu/thành tích, mỗi thành tích có kiểm tra thích hợp cho các điều kiện mà nó sẽ được trao.

Lý do tôi đề xuất bạn di chuyển ra khỏi mô hình bạn đang xem hiện tại (một lớp cho mỗi thành tích) là vì bạn sẽ tiếp tục gặp phải các vấn đề lớn khi bạn đang điều hướng qua 200 các lớp khác nhau tìm kiếm một ID mà bạn không thể nhớ lại.

Bằng cách lưu trữ huy hiệu của bạn trong bảng, dữ liệu của bạn là tất cả ở một nơi hợp lý và không nằm rải rác trên ứng dụng của bạn.

Trong câu trả lời cho câu hỏi: Vì vậy, làm bạn không đồng ý với câu trả lời chấp nhận: stackoverflow.com/questions/3162446/

Không nhất thiết, và tôi thích ý tưởng này hơn đề nghị trước đó của tôi cho một lớp học duy nhất mà sẽ rà soát tất cả các huy hiệu dựa trên ID của họ.

Mặc dù tên của nó, tôi tin rằng RexM không tự xác định CommenterBadge trong tệp đó và nên đặt tên là CommenterBadgeJob. (Bạn sẽ nhận thấy nó không có những đặc điểm mà tôi đã xác định trong câu trả lời của tôi và thừa kế từ BadgeJob). Câu hỏi rõ ràng là "Làm thế nào mỗi công việc của huy hiệu biết Huy hiệu nào tương ứng với nó?"

Tôi sẽ có một trường duy nhất bổ sung trong số Badge được gọi là BadgeJob mà bạn có thể tra cứu huy hiệu.

enum BadgeClass {Bronze, Silver, Gold} 

//This class would be inherited from the database. 
public class Badge 
{ 
    public int Key {get;set;} 
    public string Name {get;set;} 
    public BadgeClass Class {get;set;} 
    public string BadgeJob {get;set;} 
    public string Description {get;set} 
} 

tôi sẽ sửa đổi mã của ông như sau:

public class CommenterBadgeJob : BadgeJob 
{ 
    public Badge commenter_badge {get;set;} 
    public CommenterBadgeJob() : base() 
    { 
     //Lookup badge 
     string badge_job_name = this.GetType().Name; 
     commenter_badge = db.Badges.Where(n=>n.BadgeJob == badge_job_name).Single(); 
    } 

    protected override void AwardBadges() 
    { 
     //select all users who have more than x comments 
     //and dont have the commenter badge 
     //add badges 
    } 

    //run every 10 minutes 
    protected override TimeSpan Interval 
    { 
     get { return new TimeSpan(0,10,0); } 
    } 
} 
+0

Vì vậy, bạn có đồng ý với câu trả lời được chấp nhận cho http://stackoverflow.com/questions/3162446/how-to-implement-badges?rq=1 không? – Tesserex

+0

Tôi đã cập nhật câu trả lời của mình. Nếu tôi không rõ ràng, hãy cho tôi biết và tôi sẽ cố gắng và sửa lại câu trả lời của tôi thêm nữa. – JoshVarty

+0

Tôi đã chuyển tất cả dữ liệu trong DB, hoạt động tốt vì phần lớn thành tích của tôi sẽ có các điều kiện đơn giản, như một số trường> = ngưỡng. Cảm ơn! – Tesserex

2

Làm thế nào về việc sử dụng enum?

public enum BadgeTypes 
    { 
     GoodAnswer = 1, 
     Commenter  = 2, 
     Teacher  = 3, 
     //... 
    } 

Mỗi BadgeJob có thể có một tài sản đó sẽ được sử dụng để cư id huy hiệu khi chèn một thành tựu trong AwardBadges() (giá trị enum có thể được tiếp tục tồn để nguyên) BadgeType.

Tôi thấy không cần thiết phải có một lớp cho mỗi thành tích. BadgeJob chứa tất cả logic phân bổ huy hiệu và BadgeTypes đủ để đại diện cho các huy hiệu khác nhau.

+0

Nhưng sau đó không có một lớp 'Job' cho mỗi thành tích? Điều đó có vẻ giống như vậy ... Tôi không muốn một lớp "Logic" dài tới hàng ngàn dòng. – Tesserex

+0

Có một lớp công việc cho mỗi thành tích ("** ** ** của ** chứa ** ... là số nhiều). Xin lỗi nếu điều đó không rõ ràng. – guillaume31

+0

Hoặc, bạn có nghĩa là, bạn không muốn một lớp công việc cho mỗi thành tích? Tôi không thấy làm thế nào điều này sẽ ngắn hơn:/ – guillaume31

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