Как сделать полную матрицу с 2 циклами в c ++ - PullRequest
1 голос
/ 24 января 2012

У меня есть строка в c ++, и она представляет верхнюю треугольную матрицу. Что я хочу сделать, так это получить полную матрицу из этой строки

    std::string input = "1,2,1,3,6,1,4,7,9,1";
    //this represents


 //1  2  3 4
 //2  1  6 7
 //3  6  1 9
 //4  7  9 1

std::replace(input.begin(), input.end(), ',', ' ');
std::vector<double> Matrix;
std::istringstream inputStream(input);
double value;
int rowNum = 0;
int colNum = 0; 

while (inputStream >> value){
    for (colNum = 0; colNum < 2; colNum++){
        if (colNum >= rowNum){
            Matrix.push_back( value ); 
        }
        else{
            Matrix.push_back( Matrix[colNum * 2 + rowNum]); 
        }
    }

    rowNum++;
}
inputStream >> std::ws;

Вместо получения

 1  2  3 4
 2  1  6 7
 3  6  1 9
 4  7  9 1

Но я получаю

   1.0000   1.0000   1.0000   2.0000
   1.0000   1.0000   2.0000   1.0000
   1.0000   2.0000   1.0000   1.0000
   2.0000   1.0000   1.0000   2.0000

В чем моя ошибка? Я не могу видеть это ...

Ответы [ 2 ]

1 голос
/ 24 января 2012

Вы должны показать схему индексирования, используемую для печати выходных данных (т.е. как вы ожидаете, что индексы работают): ваш выбор использования вектора вместо матрицы затруднит корректировку кода.Конечно, я вижу следующие моменты, которые не имеют четкой связи с шаблоном ввода:

1) с каждым прочитанным числом вы увеличиваете индекс rowNum.Вместо этого строка должна быть увеличена с шагом 1, 1 + 2, 1 + 2 + 3, ...

2) colNum должен находиться в диапазоне от 0 до текущего rowNum, вместо этого предполагается, что он равен 0,1 * 1005.*

3) нет возможности заполнить строку (скажем, первую), прежде чем читать (скажем, последнюю).Вы могли бы сделать, если бы ввод был 1 2 3 4 1 6 7 1 9 1

, все эти точки связаны и происходят из-за неправильного представления данных, что усложняет тривиальную задачу.

В C ++ очень эффективным способом решения этих проблем является сокрытие данных: подумайте, как легко мы можем написать класс, который дает правильное логическое представление и не тратит пространство:

#include <iostream>
#include <sstream>
#include <string>
#include <vector>
#include <algorithm>

template <class T = double>
class upper_triangular_matrix
{
    std::vector<T> Matrix;

public:

    upper_triangular_matrix(std::string input)
    {
        // trade time for space: store the values, compute indexing
        std::replace(input.begin(), input.end(), ',', ' ');
        std::istringstream inputStream(input);
        T value;
        while (inputStream >> value)
            Matrix.push_back(value);

        // validate size: ok 1,1+2,1+2+3 etc
    }

    T operator()(int r, int c) const
    {
        // compute indexing accounting for miss duplicated
        if (c > r)
            std::swap(c, r);
        int p = 0, n = 1;
        while (r > 0)
        {
            p += n++;
            r--;
        }
        return Matrix[p + c];
    }
};

int main()
{
    upper_triangular_matrix<> m("1,2,1,3,6,1,4,7,9,1");
    for (int r = 0; r < 4; ++r)
    {
        for (int c = 0; c < 4; ++c)
            std::cout << m(r, c) << ' ';
        std::cout << std::endl;
    }
}

при запуске, этоотпечатки

1 2 3 4 
2 1 6 7 
3 6 1 9 
4 7 9 1 
0 голосов
/ 24 января 2012

Трудно сказать точно, где ошибка, но вот где она начинается:

std::vector<double> Matrix;

Да, непустая std::vector<double> с n элементами - это матрица: матрица 1xn или nx1 (или обе). В вашем контексте это мнение, однако, совершенно бесполезно.

Давайте посмотрим на for -loop, когда вы читаете первый элемент:

  1. colNum == 0, rowNum == 0 => (1, 1) = Matrix [0] = 1
  2. colNum == 1, rowNum == 0 => (2, 1) = Matrix [1] = 1

Этот старт явно неправильный. После этого rowNum становится 1:

  1. colNum == 0, rowNum == 1 => (3, 1) = Matrix [2] = Matrix [colNum * 2 + rowNum] = Matrix [1] = 1
  2. colNum == 1, rowNum == 1 => (4, 1) = Matrix [3] = 2

Ну, я думаю, вы можете сами написать остаток. Конечно, я мог бы быстро написать код для решения вашей проблемы, но я думаю, что это небольшое упражнение для вас. Способ сделать это - заполнить первые row столбцы (где row - текущая обрабатываемая строка с использованием обычного индекса, начинающегося с 0) значениями из транспонированной матрицы, а затем прочитать оставшиеся n - row столбцы (где n - размер матрицы) из файла.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...