leetcode #48 in cpp

This is to rotate a matrix clockwise with 90 degree.


Solution 1: Naive rotate

Suppose the input is a n*n matrix. Then the ith row should be put to (n - 1 - i)th column. 

For example n =3. Then 0th row to 2nd column. 1th row to 1th column. 2th row to 0th column. 

We can create an empty matrix and move rows from original matrix to columns in this empty matrix.

void naive_rotate(vector<vector<int>>& matrix){
        vector<vector<int>> temp(matrix.size(), vector<int>(matrix.size()));
        for(int r = 0; r < matrix.size(); r ++){
            int c = 0;
            while(c<matrix.size()){
                temp[c][matrix.size() - 1 - r] = matrix[r][c];
                c++;
            }
        }
        matrix = temp;
    }



Solution 2: Rotate in place

From solution 1 we know that ith row would be moved to n-1-i th column. 

How does it look like if we do so in place? 

Example:

123
456
789
Figrue 1.

Move the 0th row to 2nd column. 

121
452
783

We have successfully created the new 3rd column. But up to this point, we have also lost the last elements of other rows. In the future these rows would not construct correct new columns. So we conclude that before we move, we have to store some values such that we won't lose any information in the future moves.

Moving a row at a time is complex. Let's try move 1 element. Say matrix[i][j].

2.1 Since ith row would be moved to n - 1 - ith column, matrix[i][j] would be moved to n - 1 - i th column. 

2.2 Suppose when we rotate a horizontal row clockwise to a vertical column, the ith cell in the row would remain at ith cell in the column. 

1  

1
 
 

By 2.1 and 2.2,  we conclude that matrix[i][j] would be moved to matrix[ j ][ n - 1 - i]. 

Now let's see what happens when we move matrix[i][j] to matrix[ n-1-j ][i]. 

(1) We record temp = matrix[ j][ n-1-i ] and matrix[i][j] moved to matrix[ j ][ n-1-i ].

(2) We need to put the record temp to its new place otherwise we lose it. Its original position is r = j, c = n-1-i, and its new position is r = n - 1 - i, c =n-1- j. Thus swap(temp, matrix[n-1-i][n-1-j]).

(3) now where should we put the new temp? Its original position is r = n-1-i, c =n-1- j and new position is r = n-1-j, i. Then swap( temp, matrx[ n-1-j ][ i ]).

(4) The original position of the new temp is r = n-1-j, c = i and new position is r = i, c = j. Note that we were first rotating matrix[i][j] and now we are back!

Thus we know that rotating mat[i][j] involves 4 swapping.

In conclusion every time we want to rotate mat[i][j], we need to do 4 swapping or otherwise we lose some values.


One extra thing to note is how the matrix changes during we rotate row by row using methods above. 

1234
5678
9101112
13141516


As we finish rotating all elements in row 1, we get

13951
14672
1510113
161284

We are just changing its border and the submatrix insider is not modified( {[6,7], [10,11]} ). 

So we know that every time we rotate a row by methods above, we would modify only the border of the square-submatrix surrounded by the row. 


Code: 


class Solution {
public:
    void rotate(vector<vector<int>>& matrix) {
        in_place_rotate(matrix, 0,matrix.size()-1, matrix.size() );
    }
    
    void in_place_rotate(vector<vector<int>> &matrix,int r_start,int r_end, int matlen){
        if(r_start>r_end - 1) return;//there is no submatrix any more. 
        for(int col = r_start; col<r_end;col++){//for current row, rotate all its components.  
<span style="white-space:pre">					</span>//IT IS VERY IMPORTANT THAT col<r_end. We do not rotate mat[r_start][r_end] 
<span style="white-space:pre">					</span>//since this position has been swapped with mat[r_start][r_start].
            int i = r_start;
            int j = col;
            int count = 0;
            int temp = matrix[i][j];//the component, mat[i][k], which we want to rotate
            while(count < 3){//if we want to rotate one component, we need to take care of 4 
                           //components since we are rotating in place
                matrix[i][j] = matrix[matlen - 1 - j ][i];
                j = matlen- 1 - j;
                swap(i,j);
                count++;
            }
            matrix[i][j] = temp;//the 4th swap 
        }
        in_place_rotate(matrix, r_start + 1, r_end - 1,matlen);//go to the next submatrix surrounded by r_start + 1.
    }
    
};



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值