【问题标题】:Refactoring Code to reflect inheritance heirarchy重构代码以反映继承层次结构
【发布时间】:2019-02-04 21:45:46
【问题描述】:

我正在尝试重构代码,但由于我对编程非常陌生,因此不知道从哪里开始。

我已经尝试将方法注释,喜欢和不一样放在 CommentedPost 类下,但不知道该怎么做。

Post.java

public class Post {
private String username;  // username of the post's author
private long timestamp;
private int likes;
private ArrayList<String> comments;

/**
 * Constructor for objects of class Post.
 * 
 * @param author    The username of the author of this post.
 */
public Post(String author)
{
    username = author;
    timestamp = System.currentTimeMillis();
    likes = 0;
    comments = new ArrayList<String>();
}

/**
 * Record one more 'Like' indication from a user.
 */
public void like()
{
    likes++;
}

/**
 * Record that a user has withdrawn his/her 'Like' vote.
 */
public void unlike()
{
    if (likes > 0) {
        likes--;
    }
}

/**
 * Add a comment to this post.
 * 
 * @param text  The new comment to add.
 */
public void addComment(String text)
{
    comments.add(text);
}

/**
 * Return the time of creation of this post.
 * 
 * @return The post's creation time, as a system time value.
 */
public long getTimeStamp()
{
    return timestamp;
}

/**
 * Display the details of this post.
 * 
 * (Currently: Print to the text terminal. This is simulating display 
 * in a web browser for now.)
 */
public void display()
{
    System.out.println(username);
    System.out.print(timeString(timestamp));

    if(likes > 0) {
        System.out.println("  -  " + likes + " people like this.");
    }
    else {
        System.out.println();
    }

    if(comments.isEmpty()) {
        System.out.println("   No comments.");
    }
    else {
        System.out.println("   " + comments.size() + " comment(s). Click here to view.");
    }
}

/**
 * Create a string describing a time point in the past in terms 
 * relative to current time, such as "30 seconds ago" or "7 minutes ago".
 * Currently, only seconds and minutes are used for the string.
 * 
 * @param time  The time value to convert (in system milliseconds)
 * @return      A relative time string for the given time
 */

private String timeString(long time)
{
    long current = System.currentTimeMillis();
    long pastMillis = current - time;      // time passed in milliseconds
    long seconds = pastMillis/1000;
    long minutes = seconds/60;
    if(minutes > 0) {
        return minutes + " minutes ago";
    }
    else {
        return seconds + " seconds ago";
    }
}
}

CommentedPost.java

public class CommentedPost extends Post {

public CommentedPost(String author) {
    super(author);
    // TODO Auto-generated constructor stub
}
}

EventPost.java

public class EventPost extends Post{

public EventPost(String author) {
    super(author);
    // TODO Auto-generated constructor stub
}

}

MessagePost.java

public class MessagePost extends Post{
private String message;  // an arbitrarily long, multi-line message

/**
 * Constructor for objects of class MessagePost.
 * 
 * @param author    The username of the author of this post.
 * @param text      The text of this post.
 */
public MessagePost(String author, String text)
{
    super(author);
    message = text;
}

/**
 * Return the text of this post.
 * 
 * @return The post's message text.
 */
public String getText()
{
    return message;
}

/**
 * Display the details of this post.
 * 
 * (Currently: Print to the text terminal. This is simulating display 
 * in a web browser for now.)
 */
public void display()
{
    super.display();
    System.out.println(message);
}
}

StartNetwork.java

public class StartNetwork{

/**
 * @param args
 */
public static void main( String[] args )
{
    MessagePost message = new MessagePost("White Rabbit", "Oh dear, oh dear, I shall be late!");
    PhotoPost photo = new PhotoPost("Alice Wonderland", "RabbitHole.jpg" ,"Down the rabbit hole :)");

    message.addComment( "Your watch is exactly two days slow." );
    photo.like();

    NewsFeed news = new NewsFeed();

    news.addPost( message );
    news.addPost( photo );
    news.show();
}   
}

PhotoPost.java

public class PhotoPost extends Post{
private String filename;  // the name of the image file
private String caption;   // a one line image caption

/**
 * Constructor for objects of class PhotoPost.
 * 
 * @param author    The username of the author of this post.
 * @param filename  The filename of the image in this post.
 * @param caption   A caption for the image.
 */
public PhotoPost(String author, String filename, String caption)
{
    super(author);
    this.filename = filename;
    this.caption = caption;
}

/**
 * Return the file name of the image in this post.
 * 
 * @return The post's image file name.
 */
public String getImageFile()
{
    return filename;
}

/**
 * Return the caption of the image of this post.
 * 
 * @return The image's caption.
 */
public String getCaption()
{
    return caption;
}

/**
 * Display the details of this post.
 * 
 * (Currently: Print to the text terminal. This is simulating display 
 * in a web browser for now.)
 */
public void display()
{
    super.display();
    System.out.println("  [" + filename + "]");
    System.out.println("  " + caption);
}
}

NewsFeed.java

public class NewsFeed{
private ArrayList<Post> posts;

/**
 * Construct an empty news feed.
 */
public NewsFeed()
{
    posts = new ArrayList<Post>();
}

/**
 * Add a post to the news feed.
 * 
 * @param post  The post to be added.
 */
public void addPost(Post post)
{
    posts.add(post);
}

/**
 * Show the news feed. Currently: print the news feed details
 * to the terminal. (To do: replace this later with display
 * in web browser.)
 */
public void show()
{
    // display all posts
    for(Post post : posts) {
        post.display();
        System.out.println();   // empty line between posts
    }
}
}

重构后的代码应该有一个类图,包含以下内容:

带有用户名和时间戳字段的帖子

CommentedPost(指向 Post 的箭头,即从它继承)w/ 字段喜欢和 cmets

EventPost(指向 Post 的箭头)带字段 eventType

带有字段消息的消息帖子(指向 CommentedPost 的箭头)

PhotoPost(指向 CommentedPost 的箭头)w/ 字段文件名和标题

【问题讨论】:

  • 您似乎添加了 StartNetwork 类而不是 Post 类的代码。
  • 您在文本中说 MessagePost 继承自 CommentedPost,但在您的代码中却没有。
  • 我没有对代码进行更改,因为我不确定如何继续。文字是说我必须做的,但我面临困难
  • @PimvanLeeuwen 我已编辑以包含正确的代码,我的错

标签: java inheritance class-hierarchy


【解决方案1】:

帖子包含喜欢和 cmets。您应该将这些字段移至 CommentedPost。

我不确定 eventType 字段是什么,但 EventPost 没有这样的字段。你应该创建它。

根据您的描述,MessagePost 应该扩展 CommentedPost。它不是;相反,它扩展了 Post。您应该更改它以扩展 CommentedPost。

根据您的描述,PhotoPost 应该扩展 CommentedPost。它不是;相反,它扩展了 Post。您应该更改它以扩展 CommentedPost。

【讨论】:

  • 我已经做了相应的操作,但是将like和cmets字段移到CommentedPost后,现在Post中的显示方式出现错误。我是否将文件移回并将它们更改为受保护而不是私有?
  • 那是因为显示方法仍然假定 Post 类具有这些字段。当您像这样重构代码(将内容移入子类)时,您还希望将功能移入子类。在这种情况下,以 CommentedPost 而不是 Post 的(新)显示方法显示字段。
  • 对不起,但这是否意味着我将显示方法复制到评论帖子中并在帖子中删除它?因为我认为这样做之后我必须将字段用户名和时间戳更改为在 Post 中受保护?
  • 您确实应该将其复制到 CommentedPost 并保护这些字段。但是,您不应该从 Post 中删除该方法;这是不好的做法。这是因为您希望其他对象知道所有 Post 对象(包括 CommentedPost 对象)都具有此方法,并且当 Post 类型未知时其他对象可以可靠地调用该方法。
  • 哦,好吧,我现在明白为什么了。不幸的是,Post 中的显示方法仍然存在相同的错误,指出无法将 like 和 cmets 解析为变量(我猜这是因为它们已被移至 CommentedPost?)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-12-22
  • 1970-01-01
  • 1970-01-01
  • 2011-06-16
  • 2020-10-24
  • 1970-01-01
相关资源
最近更新 更多