2

I'm currently doing my third year programming project and its a folio tracker. :/ I have crated Stock_API and Portfolio_API interfaces (and implementations of them) and a GUI class which when instantiated takes two parameters as so:

public GUI(Portfolio_API p, Stock s){
      tempPort = p;
      tempStock = s;
}

I use this constructor as a way of getting implementations of these interfaces into the GUI without exposing the implementation to the GUI (which is one of the main objectives of this project). A portfolio object has a name(string) and an ArrayList. A stock object has a ticker symbol(string), a stock name(string), a share value(float), a number of shares(int) and a value of holding(float).

In the GUI i have a portCollection array list which holds objects of type portfolio_API and this is so the system can keep track of multiple portfolios. Also as mentioned in the block of code above has a tempStock and tempPort object.

Sorry to give u so much detail about the program but i thought it best so i could get the context across. Anyway, the problem at hand. I have a method which uses the GUI to get a ticker symbol, a stock name and a number of shares and adds the stock to the current portfolio open(each portfolio has its own tab). The method looks like this:

public void addStock() {
    int num_shares = 0;
    float dailyChange = 0.0f;
    float stockValue = 0.0f;
    boolean succeed = true;

    // GUI gets information of stock from user
    String ticker = JOptionPane.showInputDialog(frame,
            "Enter the ticker symbol:");
    String stockName = JOptionPane.showInputDialog(frame,
            "Enter the Stock name:");
    try {
        num_shares = Integer.parseInt(JOptionPane.showInputDialog(frame,
                "Enter the number of shares:"));
    } catch (NumberFormatException e) {
        JOptionPane.showMessageDialog(frame,
                "Number of shares was not an integer. Try again");
        succeed = false;
    }

    // If parsing was successful...
    if (succeed) {
        tempStock.setTicker(ticker);
        tempStock.setNumberOfShares(num_shares);
        tempStock.setStockName(stockName);

        // Fetches newest value using the current ticker symbol
        boolean succeedUpdate = tempStock.updateShareValue();

        if (succeedUpdate) {
            tempStock.calculateValueOfHolding();

            // Adds to the current portfolio...
            String tabName = tabbedPane.getTitleAt(tabbedPane
                    .getSelectedIndex());
            System.out.println(tabName);
            findPortfolio(tabName).addStock(tempStock);
            findPortfolio(tabName).sort();

            // ...Then adds it to the table
            JPanel j = (JPanel) tabbedPane.getSelectedComponent()
                    .getComponentAt(0, 0);
            JViewport v = ((JScrollPane)   j.getComponent(0)).getViewport();
            JTable table = (JTable) v.getComponent(0);

            float currentTotal = findPortfolio(tabName).getTotal();

            // Updates the total label
            ((JLabel) j.getComponent(1)).setText("Total: " + currentTotal);

            Object[] newStock = { tempStock.getTicker(),
                    tempStock.getStockName(),
                    tempStock.getNumberOfShares(),
                    tempStock.getShareValue(),
                    tempStock.getValueOfHolding() };
            ((DefaultTableModel) table.getModel()).addRow(newStock);
        }
    }
}

When I add more than one stock, the new stock takes place of the old one an effectively overwrites it. I think its the reuse of tempStock that is doing it. Not sure why though as surely if i add the variable to an arraylist it becomes part of that arraylist and needs no association with the tempStock variable?

Methods that are used with the mentioned arraylists :

private Portfolio_API findPortfolio(String name) {
        Portfolio_API p = null;
        for (int i = 0; i < portCollection.size(); i++) {
            if (portCollection.get(i).getName() == name) {
                p = portCollection.get(i);
            }
        }

These two are in the Portfolio class:

@Override
public boolean addStock(Stock_API s) {
    if (!doesExist(s)) {
        portfolio.add(s);
        return true;
    } else {
        return false;
    }

}

@Override
public boolean doesExist(Stock_API s) {
    boolean found = false;
    for (int i = 0; i < portfolio.size(); i++) {
        if (portfolio.get(i).getTicker() == s.getTicker()) {
            found = true;
        }
    }
    return found;
}

I've only come here for help because i have hit a brick wall and I really need help. If anyone could give me any suggestions, i'd be eternally in your debt.

Thanks, Chris

4
  • 4
    You haven't shown any code which uses an ArrayList, which makes it hard to pin this down... Commented Dec 11, 2010 at 19:53
  • Ah sorry, will edit the post and add a few methods that use an arraylist. Commented Dec 11, 2010 at 19:58
  • 3
    When you "add" an object to a list, you add a reference to that object, not a copy of the object. If you later change the object, all references to that object will see that change. Commented Dec 11, 2010 at 20:15
  • 1
    Thanks, i thought thats what was happening but wasnt sure. Thanks for confirming. Commented Dec 11, 2010 at 20:26

2 Answers 2

3

Yes, I think you are right when you say you think it's because you're reusing the tempStock variable. This variable still references the original object so calling setTicker() etc on tempStock also changes the object referenced by your ArrayList because it's the same object. Try reinitialising your tempStock and see if it makes a difference:

// If parsing was successful...
    if (succeed) {
        tempStock = new Stock(); // or however you instantiate this object
        tempStock.setTicker(ticker);
        tempStock.setNumberOfShares(num_shares);
        tempStock.setStockName(stockName);
Sign up to request clarification or add additional context in comments.

2 Comments

I would but by re initialising i would have to do tempStock = new Stock(); but this would expose the implementation to the GUI :/ I wish there was a way to do tempStock = new Stock_API() but of course being an interface, you cant initailise it.
You could overload the Portfolio class's addStock() to take the stock data addStock(Ticker ticker, int numOfShares, String name) and build it in there
0

Thanks guys for all your input. @oracle certified professor helped with the stock problems after adding an overloaded method for addStock but turned out the same problems plagued portfolio.

What I did was create a makePortfolio method in Portfolio_API to create a new portfolio and return it. That way it avoids any nasty overwrite, gonna add it to stock too just now.

Thanks again guys. Good night! :)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.