Try Our Course for 4 Hours @99rs

Try our course for 4 Hours and if you like it, you can go for one year or lifetime access. If you buy our (1yr or lifetime) course 99rs will be refunded !

Design (LLD) Stack Overflow - Machine Coding Interview

Design (LLD) Stack Overflow - Machine Coding Interview

maxresdefault.jpeg

Stack Overflow

Stack Overflow is one of the largest online communities for developers to learn and share their knowledge. The website provides a platform for its users to ask and answer questions, and through membership and active participation, to vote questions and answers up or down. Users can edit questions and answers in a fashion similar to a wiki.

Features

We will be designing a system with the following requirements:

  1. Any non-member (guest) can search and view questions. However, to add or upvote a question, they have to become a member.

  2. Members should be able to post new questions.

  3. Members should be able to add an answer to an open question.

  4. Members can add comments to any question or answer.

  5. A member can upvote a question, answer or comment.

  6. Members can flag a question, answer or comment, for serious problems or moderator attention.

  7. Any member can add a bounty to their question to draw attention.

  8. Members will earn badges for being helpful.

  9. Members can vote to close a question; Moderators can close or reopen any question.

  10. Members can add tags to their questions. A tag is a word or phrase that describes the topic of the question.

  11. Members can vote to delete extremely off-topic or very low-quality questions.

  12. Moderators can close a question or undelete an already deleted question.

  13. The system should also be able to identify most frequently used tags in the questions.

Rough Solution (LLD-Machine Coding)

// Enum classes remain the same
public enum QuestionStatus {
    OPEN,
    CLOSED,
    ON_HOLD,
    DELETED
}

public enum QuestionClosingRemark {
    DUPLICATE,
    OFF_TOPIC,
    TOO_BROAD,
    NOT_CONSTRUCTIVE,
    NOT_A_REAL_QUESTION,
    PRIMARILY_OPINION_BASED
}

public enum AccountStatus {
    ACTIVE,
    CLOSED,
    CANCELED,
    BLACKLISTED,
    BLOCKED
}

public enum PaymentStatus {
    UNPAID,
    PENDING,
    COMPLETED,
    FAILED,
    DECLINED,
    CANCELLED,
    SETTLED,
    REFUNDED
}


// Observer Pattern for notifications
interface Observer {
    void update(String message);
}

class Member implements Observer {
    private Account account;
    private List<Badge> badges;

    public int getReputation() {
        return account.getReputation();
    }

    public String getEmail() {
        return account.getEmail();
    }

    @Override
    public void update(String message) {
        System.out.println("Notification for Member: " + account.getName() + ": " + message);
    }

    public boolean createQuestion(Question question) {
        // Question creation logic
        return true;
    }

    public boolean createTag(Tag tag) {
        // Tag creation logic
        return true;
    }
}

class Admin extends Member {
    public boolean blockMember(Member member) {
        member.getAccount().setStatus(AccountStatus.BLOCKED);
        System.out.println("Member " + member.getAccount().getName() + " has been blocked.");
        return true;
    }

    public boolean unblockMember(Member member) {
        member.getAccount().setStatus(AccountStatus.ACTIVE);
        System.out.println("Member " + member.getAccount().getName() + " has been unblocked.");
        return true;
    }
}

class Moderator extends Member {
    public boolean closeQuestion(Question question) {
        question.setStatus(QuestionStatus.CLOSED);
        System.out.println("Question has been closed.");
        return true;
    }

    public boolean undeleteQuestion(Question question) {
        question.setStatus(QuestionStatus.OPEN);
        System.out.println("Question has been undeleted.");
        return true;
    }
}

// Factory Method Pattern for creating different objects
abstract class MemberFactory {
    public abstract Member createMember(Account account);
}

class AdminFactory extends MemberFactory {
    @Override
    public Admin createMember(Account account) {
        return new Admin(account);
    }
}

class ModeratorFactory extends MemberFactory {
    @Override
    public Moderator createMember(Account account) {
        return new Moderator(account);
    }
}

class QuestionFactory {
    public static Question createQuestion(String title, String description, Member askingMember) {
        return new Question(title, description, askingMember);
    }
}

// Command Pattern for actions like voting, closing, etc.
interface Command {
    void execute();
}

class CloseQuestionCommand implements Command {
    private Moderator moderator;
    private Question question;

    public CloseQuestionCommand(Moderator moderator, Question question) {
        this.moderator = moderator;
        this.question = question;
    }

    @Override
    public void execute() {
        moderator.closeQuestion(question);
    }
}

class AddCommentCommand implements Command {
    private Question question;
    private Comment comment;

    public AddCommentCommand(Question question, Comment comment) {
        this.question = question;
        this.comment = comment;
    }

    @Override
    public void execute() {
        question.addComment(comment);
    }
}

class IncrementVoteCommand implements Command {
    private Votable item;

    public IncrementVoteCommand(Votable item) {
        this.item = item;
    }

    @Override
    public void execute() {
        item.incrementVoteCount();
    }
}

// Template Method Pattern for voting and flagging
abstract class Votable {
    private int voteCount = 0;
    private int flagCount = 0;

    public final void incrementVoteCount() {
        this.voteCount++;
    }

    public final void incrementFlagCount() {
        this.flagCount++;
    }

    public int getVoteCount() {
        return voteCount;
    }

    public int getFlagCount() {
        return flagCount;
    }

    // Subclasses must implement specific behavior for voting
    protected abstract void notifyOnVote();
}

class Question extends Votable {
    private String title;
    private String description;
    private int viewCount;
    private Date creationTime;
    private Date updateTime;
    private QuestionStatus status;
    private Member askingMember;

    private List<Comment> comments;
    private List<Answer> answers;

    public Question(String title, String description, Member askingMember) {
        this.title = title;
        this.description = description;
        this.askingMember = askingMember;
        this.status = QuestionStatus.OPEN;
    }

    @Override
    protected void notifyOnVote() {
        System.out.println("Question voted: " + this.title);
    }

    public boolean close() {
        this.status = QuestionStatus.CLOSED;
        return true;
    }

    public boolean undelete() {
        this.status = QuestionStatus.OPEN;
        return true;
    }

    public boolean addComment(Comment comment) {
        comments.add(comment);
        return true;
    }

    public boolean addAnswer(Answer answer) {
        answers.add(answer);
        return true;
    }
}

class Answer extends Votable {
    private String answerText;
    private boolean accepted;
    private Date creationTime;
    private Member creatingMember;

    @Override
    protected void notifyOnVote() {
        System.out.println("Answer voted.");
    }
}

// Strategy Pattern for search
interface SearchStrategy {
    List<Question> search(List<Question> questions, String query);
}

class TitleSearchStrategy implements SearchStrategy {
    @Override
    public List<Question> search(List<Question> questions, String query) {
        List<Question> result = new ArrayList<>();
        for (Question question : questions) {
            if (question.getTitle().contains(query)) {
                result.add(question);
            }
        }
        return result;
    }
}

class TagSearchStrategy implements SearchStrategy {
    @Override
    public List<Question> search(List<Question> questions, String query) {
        // Implementation for searching by tag
        return new ArrayList<>();
    }
}

// Supporting Classes
public class Comment extends Votable {
    private String text;
    private Date creationTime;
    private Member askingMember;

    @Override
    protected void notifyOnVote() {
        System.out.println("Comment voted: " + this.text);
    }
}

public class Account {
    private String id;
    private String password;
    private AccountStatus status;
    private String name;
    private Address address;
    private String email;
    private String phone;
    private int reputation;

    public boolean resetPassword() {
        // Reset password logic
        return true;
    }

    public String getName() {
        return name;
    }

    public void setStatus(AccountStatus status) {
        this.status = status;
    }

    public AccountStatus getStatus() {
        return status;
    }

    public int getReputation() {
        return reputation;
    }

    public String getEmail() {
        return email;
    }
}

public class Notification {
    private int notificationId;
    private Date createdOn;
    private String content;

    public boolean sendNotification() {
        // Sending notification logic
        return true;
    }
}

// Main class to demonstrate
public class Main {
    public static void main(String[] args) {
        // Create some members
        Account adminAccount = new Account();
        Admin admin = new Admin(adminAccount);

        Account modAccount = new Account();
        Moderator moderator = new Moderator(modAccount);

        // Create a question using Factory Method
        Question question = QuestionFactory.createQuestion("What is Java?", "Description of Java.", moderator);

        // Close question using Command Pattern
        Command closeQuestionCommand = new CloseQuestionCommand(moderator, question);
        closeQuestionCommand.execute();

        // Add comment using Command Pattern
        Comment comment = new Comment();
        Command addCommentCommand = new AddCommentCommand(question, comment);
        addCommentCommand.execute();

        // Vote on a question using Template Method Pattern
        Command voteCommand = new IncrementVoteCommand(question);
        voteCommand.execute();
    }
}