dcsimg
CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Page 2 of 2 FirstFirst 12
Results 16 to 21 of 21

Thread: Sparse Matrix Operations

  1. #16
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    6,922

    Re: Sparse Matrix Operations

    Code:
    R.elems[nr].Linie = new int[nr]; 
    R.elems[nr].Coloana = new int[nr];
    R.elems[nr].Valoare = new double[nr];
    I think you require
    Code:
    R.elems.resize(nr);
    since elems is a vector.
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2019 (16.4.0)

  2. #17
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    6,922

    Re: Sparse Matrix Operations

    Unless I've misunderstood what you are trying to achieve, you seem to be making very heavy weather of doing this. Consider the code below which reads in 2 files in the .mtx format, displays their contents, produces a new matrix which is their sum and displays this matrix. Various improvements could be made to this code which I'll leave to you.

    Code:
    #include <iostream>
    #include <fstream>
    #include <string>
    using namespace std;
    
    const string fa = "mata.mtx";
    const string fb = "matb.mtx";
    
    class matrix {
    public:
    	matrix(int col, int row) : cols(col), rows(row), elems(new double[col * row])
    	{
    		memset(elems, 0, sizeof(double) * col * row);
    	}
    
    	~matrix() {
    		delete[] elems;
    	}
    
    	matrix(const string& fn)
    	{
    		ifstream fma(fn);
    		if (!fma.is_open()) {
    			cout << "Cannot open " << fn << endl;
    			return;
    		}
    
    		string tmp;
    		while (fma.peek() == '%')
    			getline(fma, tmp);
    
    		int noelems;
    
    		fma >> rows >> cols >> noelems;
    		elems = new double[cols * rows];
    		memset(elems, 0, sizeof(double) * cols * rows);
    
    		int r, c;
    		double v;
    
    		while (fma >> r >> c >> v)
    			operator()(c - 1, r - 1) = v;
    
    		fma.close();
    	}
    
    	matrix(const matrix& ma)
    	{
    		cols = ma.cols;
    		rows = ma.rows;
    		elems = new double[cols * rows];
    		memcpy(elems, ma.elems, sizeof(double) * cols * rows);
    	}
    
    	matrix(matrix&& ma)
    	{
    		cols = ma.cols;
    		rows = ma.rows;
    		elems = ma.elems;
    		ma.elems = nullptr;
    	}
    
    	double& operator()(int c, int r)
    	{
    		return elems[c * cols + r];
    	}
    
    	const double& operator()(int c, int r) const
    	{
    		return elems[c * cols + r];
    	}
    
    	int noRows() const
    	{
    		return rows;
    	}
    
    	int noCols() const
    	{
    		return cols;
    	}
    
    
    	matrix operator=(matrix&&) = delete;
    	matrix operator=(const matrix&) = delete;
    
    private:
    	int cols = 0;
    	int rows = 0;
    	double *elems = nullptr;
    };
    
    ostream& operator<<(ostream& os, const matrix& ma)
    {
    	for (int r = 0; r < ma.noRows(); ++r) {
    		for (int c = 0; c < ma.noCols(); ++c)
    			os << ma(c, r) << " ";
    
    		os << endl;
    	}
    
    	return os;
    }
    
    matrix operator+(const matrix& ma, const matrix& mb)
    {
    	if ((ma.noCols() != mb.noCols()) || (ma.noRows() != mb.noRows())) {
    		cout << "cols/rows don't match" << endl;
    		return matrix(0, 0);
    	}
    
    	matrix s(ma.noCols(), ma.noRows());
    
    	for (int r = 0; r < ma.noRows(); ++r)
    		for (int c = 0; c < ma.noCols(); ++c)
    			s(c, r) = ma(c, r) + mb(c, r);
    
    	return s;
    }
    
    int main()
    {
    	matrix A(fa);
    
    	if (A.noCols() == 0)
    		return 1;
    
    	cout << "Matrix A" << endl;
    	cout << A;
    
    	matrix B(fb);
    
    	if (B.noCols() == 0)
    		return 2;
    
    	cout << endl << "Matrix B" << endl;
    	cout << B;
    
    	matrix S = A + B;
    
     	if (S.noCols() != 0) {
    		cout << endl << "Matrix sum" << endl;
    		cout << S;
    	}
    }
    Last edited by 2kaud; May 3rd, 2016 at 04:36 PM.
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2019 (16.4.0)

  3. #18
    Join Date
    Aug 2000
    Location
    West Virginia
    Posts
    7,716

    Re: Sparse Matrix Operations

    1) Since you are using std::vector, you will not need to
    do a "new" to increase the size of sum matrix. You can
    simply push_back() the element.

    2) As a first pass, I would choose a simple method:

    a) set the sum matrix equal to the first matrix.

    b) loop thru the second matrix ... for each (i,j) combination
    in the second matrix, see if the combination is in the first
    matrix. If it is, add the values. If it is not, create a
    new element and do a push_back() to the sum matrix. There
    are other containers besides std::vector that would make this
    step faster.

    Code:
    // ADDITION A + B
    MatriceRara Sum(const MatriceRara& M1, const MatriceRara& M2)
    {
        MatriceRara R;
    
        if (M1.nrLinii != M2.nrLinii || M1.nrColoane != M2.nrColoane)
        {
            cout << "Eroare: Matricele trebuie sa aiba dimensiuni egale." << endl;
    
            return R;
        }
    
        R = M1;  // set the sum equal to the first matrix
    
        // loop thru the second matrix ... if the element exists
        // in the first matrix, add it to the sum.  If it does
        // not exist, create a new element in the sum.
    
        for (int j = 0; j<M2.nrElemente; ++j)
        {
            bool found = false;
            for (int i = 0; i<M1.nrElemente; ++i)
            {
                if (M1.elems[i].Linie == M2.elems[j].Linie &&
                    M1.elems[i].Coloana == M2.elems[j].Coloana)
                {
                    found = true;
                    R.elems[i].Valoare += M2.elems[j].Valoare;
                    break;
                }
            }
    
            if (!found) // element is in M2, but not in M1
            {
                Elems el;
                el.Linie = M2.elems[j].Linie;
                el.Coloana = M2.elems[j].Coloana;
                el.Valoare = M2.elems[j].Valoare;
    
                R.elems.push_back(el);
            }
        }
    
        // remove elements that equal 0.0
        auto value_0 = [](const Elems & el) { return el.Valoare == 0.0; };
        R.elems.erase(remove_if(R.elems.begin(), R.elems.end(), value_0), R.elems.end());
    
        R.nrElemente = R.elems.size();
    
        return R;
    }

  4. #19
    Join Date
    Apr 2016
    Posts
    8

    Re: Sparse Matrix Operations

    Thank you very much !
    Now, work OK

  5. #20
    Join Date
    Jun 2009
    Location
    France
    Posts
    2,513

    Re: Sparse Matrix Operations

    Quote Originally Posted by 2kaud View Post
    Unless I've misunderstood what you are trying to achieve, you seem to be making very heavy weather of doing this.
    I believe the original goal was to get this working for sparse matrix implementations?
    Is your question related to IO?
    Read this C++ FAQ article at parashift by Marshall Cline. In particular points 1-6.
    It will explain how to correctly deal with IO, how to validate input, and why you shouldn't count on "while(!in.eof())". And it always makes for excellent reading.

  6. #21
    2kaud's Avatar
    2kaud is offline Super Moderator Power Poster
    Join Date
    Dec 2012
    Location
    England
    Posts
    6,922

    Re: Sparse Matrix Operations

    Quote Originally Posted by monarch_dodra View Post
    I believe the original goal was to get this working for sparse matrix implementations?
    Yes, but the OP's post #15 mentions converting sparse matrix to full matrix. If the full matrices can be held in memory and depending upon the size of the matrices and the number of used elements, the operations on a full matrix may be more efficient than on a sparse matrix structure. The best method in a particular situation will depend upon the size of the matrices and number of used elements.
    All advice is offered in good faith only. All my code is tested (unless stated explicitly otherwise) with the latest version of Microsoft Visual Studio (using the supported features of the latest standard) and is offered as examples only - not as production quality. I cannot offer advice regarding any other c/c++ compiler/IDE or incompatibilities with VS. You are ultimately responsible for the effects of your programs and the integrity of the machines they run on. Anything I post, code snippets, advice, etc is licensed as Public Domain https://creativecommons.org/publicdomain/zero/1.0/ and can be used without reference or acknowledgement. Also note that I only provide advice and guidance via the forums - and not via private messages!

    C++17 Compiler: Microsoft VS2019 (16.4.0)

Page 2 of 2 FirstFirst 12

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  


Windows Mobile Development Center


Click Here to Expand Forum to Full Width




On-Demand Webinars (sponsored)