📜  查找给定矩阵是否为 Toeplitz

📅  最后修改于: 2022-05-13 01:57:23.606000             🧑  作者: Mango

查找给定矩阵是否为 Toeplitz

给定一个方阵,判断它是否是 Toeplitz 矩阵。 Toeplitz(或对角常数)矩阵是一个矩阵,其中从左到右的每个下降对角线都是常数,即对角线上的所有元素都相同。
通常,如果每个单元 mat[i][j] 与 mat[i-1][j-1] 相同,则任何 n×n 矩阵 mat[][] 都是 Toeplitz 矩阵,mat[i+1][j +1], mat[i-2][j-2], mat[i+2][j+2], .. 对于每个单元 mat[i][j] 和所有有效单元 mat[i+k ][j+k] 或 mat[ik][jk]

例子 :

Input: mat[N][N] = {{ 6, 7, 8},
                    { 4, 6, 7},
                    { 1, 4, 6}},
Output : True;
Values in all diagonals are same.

Input: mat[N][N] = {{ 6, 7, 8, 9 },
                    { 4, 6, 7, 8 },
                    { 1, 4, 6, 7 },
                    { 0, 1, 4, 6 },
                    { 2, 0, 1, 4 }};
Output : True;

Input: mat[N][N] = {{ 6, 3, 8},
                    { 4, 9, 7},
                    { 1, 4, 6}},
Output : False;

这个想法很简单。对于矩阵中第一行和第一列(或最后一行和最后一列)的每个元素,我们检查从该元素开始的下降对角线是否具有相同的值。如果我们发现任何对角线具有不同的值,我们将返回 false。

下面是上述代码的实现:

C++
// C++ program to check whether given matrix
// is a Toeplitz matrix or not
#include 
using namespace std;
#define N 5
#define M 4
 
// Function to check if all elements present in
// descending diagonal starting from position
// (i, j) in the matrix are all same or not
bool checkDiagonal(int mat[N][M], int i, int j)
{
    int res = mat[i][j];
    while (++i < N && ++j < M)
    {
        // mismatch found
        if (mat[i][j] != res)
            return false;
    }
 
    // we only reach here when all elements
    // in given diagonal are same
    return true;
}
 
// Function to check whether given matrix is a
// Toeplitz matrix or not
bool isToeplitz(int mat[N][M])
{
    // do for each element in first row
    for (int i = 0; i < M; i++)
    {
        // check descending diagonal starting from
        // position (0, j) in the matrix
        if (!checkDiagonal(mat, 0, i))
            return false;
    }
 
    // do for each element in first column
    for (int i = 1; i < N; i++)
    {
        // check descending diagonal starting from
        // position (i, 0) in the matrix
        if (!checkDiagonal(mat, i, 0))
            return false;
    }
 
    // we only reach here when each descending
    // diagonal from left to right is same
    return true;
}
 
// Driver code
int main()
{
    int mat[N][M] = { { 6, 7, 8, 9 },
                      { 4, 6, 7, 8 },
                      { 1, 4, 6, 7 },
                      { 0, 1, 4, 6 },
                      { 2, 0, 1, 4 } };
 
    // Function call
    if (isToeplitz(mat))
        cout << "Matrix is a Toeplitz ";
    else
        cout << "Matrix is not a Toeplitz ";
 
    return 0;
}


Java
// Java program to check whether given matrix
// is a Toeplitz matrix or not
import java.io.*;
 
class GFG
{
    public static int N = 5;
    public static int M = 4;
 
    // Function to check if all elements present in
    // descending diagonal starting from position
    // (i, j) in the matrix are all same or not
    static boolean checkDiagonal(int mat[][], int i, int j)
    {
        int res = mat[i][j];
        while (++i < N && ++j < M)
        {
            // mismatch found
            if (mat[i][j] != res)
                return false;
        }
 
        // we only reach here when all elements
        // in given diagonal are same
        return true;
    }
 
    // Function to check whether given matrix is a
    // Toeplitz matrix or not
    static boolean isToeplitz(int mat[][])
    {
        // do for each element in first row
        for (int i = 0; i < M; i++)
        {
            // check descending diagonal starting from
            // position (0, j) in the matrix
            if (!checkDiagonal(mat, 0, i))
                return false;
        }
 
        // do for each element in first column
        for (int i = 1; i < N; i++)
        {
            // check descending diagonal starting from
            // position (i, 0) in the matrix
            if (!checkDiagonal(mat, i, 0))
                return false;
        }
 
        // we only reach here when each descending
        // diagonal from left to right is same
        return true;
    }
 
    // Driver code
    public static void main(String[] args)
    {
        int mat[][] = { { 6, 7, 8, 9 },
                        { 4, 6, 7, 8 },
                        { 1, 4, 6, 7 },
                        { 0, 1, 4, 6 },
                        { 2, 0, 1, 4 } };
 
        // Function call
        if (isToeplitz(mat))
            System.out.println("Matrix is a Toeplitz ");
        else
            System.out.println("Matrix is not a Toeplitz ");
    }
}
 
// This code is contributed by Pramod Kumar


Python3
# Python3 program to check whether given
# matrix is a Toeplitz matrix or not
N = 5
M = 4
 
# Function to check if all elements present in
# descending diagonal starting from position
# (i, j) in the matrix are all same or not
 
 
def checkDiagonal(mat, i, j):
    res = mat[i][j]
    i += 1
    j += 1
 
    while (i < N and j < M):
 
        # mismatch found
        if (mat[i][j] != res):
            return False
 
        i += 1
        j += 1
 
    # we only reach here when all elements
    # in given diagonal are same
    return True
 
# Function to check whether given
# matrix is a Toeplitz matrix or not
 
 
def isToeplitz(mat):
 
    # do for each element in first row
    for j in range(M):
 
        # check descending diagonal starting from
        # position (0, j) in the matrix
        if not(checkDiagonal(mat, 0, j)):
            return False
 
    # do for each element in first column
    for i in range(1, N):
 
        # check descending diagonal starting
        # from position (i, 0) in the matrix
        if not(checkDiagonal(mat, i, 0)):
            return False
 
    return True
 
 
# Driver Code
if __name__ == "__main__":
 
    mat = [[6, 7, 8, 9],
           [4, 6, 7, 8],
           [1, 4, 6, 7],
           [0, 1, 4, 6],
           [2, 0, 1, 4]]
 
    # Function call
    if(isToeplitz(mat)):
        print("Matrix is a Toeplitz")
    else:
        print("Matrix is not a Toeplitz")
 
# This code is contributed by Jasmine K Grewal


C#
// C# program to check whether given matrix
// is a Toeplitz matrix or not
using System;
 
class GFG {
 
    public static int N = 5;
    public static int M = 4;
 
    // Function to check if all elements present in
    // descending diagonal starting from position
    // (i, j) in the matrix are all same or not
    static bool checkDiagonal(int[, ] mat, int i, int j)
    {
 
        int res = mat[i, j];
        while (++i < N && ++j < M) {
 
            // mismatch found
            if (mat[i, j] != res)
                return false;
        }
 
        // we only reach here when all elements
        // in given diagonal are same
        return true;
    }
 
    // Function to check whether given matrix is a
    // Toeplitz matrix or not
    static bool isToeplitz(int[, ] mat)
    {
 
        // do for each element in first row
        for (int i = 0; i < M; i++) {
 
            // check descending diagonal starting from
            // position (0, j) in the matrix
            if (!checkDiagonal(mat, 0, i))
                return false;
        }
 
        // do for each element in first column
        for (int i = 1; i < N; i++) {
 
            // check descending diagonal starting from
            // position (i, 0) in the matrix
            if (!checkDiagonal(mat, i, 0))
                return false;
        }
 
        // we only reach here when each descending
        // diagonal from left to right is same
        return true;
    }
 
    // Driver code
    public static void Main()
    {
        int[, ] mat = { { 6, 7, 8, 9 },
                        { 4, 6, 7, 8 },
                        { 1, 4, 6, 7 },
                        { 0, 1, 4, 6 },
                        { 2, 0, 1, 4 } };
 
        // Function call
        if (isToeplitz(mat))
            Console.WriteLine("Matrix is a Toeplitz ");
        else
            Console.WriteLine("Matrix is not a Toeplitz ");
    }
}
 
// This code is contributed by KRV.


PHP


Javascript


C++
// C++ program to check whether given
// matrix is a Toeplitz matrix or not
#include 
using namespace std;
 
bool isToeplitz(vector> matrix)
{
     
    // row = number of rows
    // col = number of columns
    int row = matrix.size();
    int col = matrix[0].size();
     
    // HashMap to store key,value pairs
    map Map;
     
    for(int i = 0; i < row; i++)
    {
        for(int j = 0; j < col; j++)
        {
            int key = i - j;
             
            // If key value exists in the hashmap,
            if (Map[key])
            {
                 
                // We check whether the current
                // value stored in this key
                // matches to element at current
                // index or not. If not, return
                // false
                if (Map[key] != matrix[i][j])
                    return false;
            }
             
            // Else we put key,value pair in hashmap
            else
            {
                Map[i - j] = matrix[i][j];
            }
        }
    }
    return true;
}
 
// Driver code
int main()
{
    vector> matrix = { { 12, 23, -32 },
                                   { -20, 12, 23 },
                                   { 56, -20, 12 },
                                   { 38, 56, -20 } };
        
    // Function call
    string result = (isToeplitz(matrix)) ? "Yes" : "No";
     
    cout << result;
     
    return 0;
}
 
// This code is contributed by divyesh072019


Java
// JAVA program to check whether given matrix
// is a Toeplitz matrix or not
 
import java.util.*;
 
class GFG {
 
    static boolean isToeplitz(int[][] matrix)
    {
        // row = number of rows
        // col = number of columns
        int row = matrix.length;
        int col = matrix[0].length;
        // HashMap to store key,value pairs
        HashMap map
            = new HashMap();
        for (int i = 0; i < row; i++)
        {
            for (int j = 0; j < col; j++)
            {
                int key = i - j;
                // if key value exists in the hashmap,
                if (map.containsKey(key))
                {
                    // we check whether the current value
                    // stored in this key matches to element
                    // at current index or not. If not,
                    // return false
                    if (map.get(key) != matrix[i][j])
                        return false;
                }
                // else we put key,value pair in hashmap
                else {
                    map.put(i - j, matrix[i][j]);
                }
            }
        }
        return true;
    }
 
    // Driver Code
    public static void main(String[] args)
    {
        int[][] matrix = { { 12, 23, -32 },
                           { -20, 12, 23 },
                           { 56, -20, 12 },
                           { 38, 56, -20 } };
       
        // Function call
        String result = (isToeplitz(matrix)) ? "Yes" : "No";
        System.out.println(result);
    }
}


Python3
# Python3 program to check whether given matrix
# is a Toeplitz matrix or not
 
def isToeplitz(matrix):
     
    # row = number of rows
    # col = number of columns
    row = len(matrix)
    col = len(matrix[0])
     
    # dictionary to store key,value pairs
    map = {}
    for i in range(row):
        for j in range(col):
            key = i-j
             
            # if key value exists in the map,
            if (key in map):
                 
                # we check whether the current value stored
                # in this key matches to element at current
                # index or not. If not, return false
                if (map[key] != matrix[i][j]):
                    return False
             
            # else we put key,value pair in map
            else:
                map[key] = matrix[i][j]
    return True
 
# Driver Code
if __name__ == "__main__":
    matrix = [[12, 23, -32], [-20, 12, 23], [56, -20, 12], [38, 56, -20]]
     
    # Function call
    if (isToeplitz(matrix)):
        print("Yes")
    else:
        print("No")


C#
// C# program to check whether given
// matrix is a Toeplitz matrix or not
using System;
using System.Collections.Generic;  
 
class GFG{
     
static bool isToeplitz(int[,] matrix)
{
     
    // row = number of rows
    // col = number of columns
    int row = matrix.GetLength(0);
    int col = matrix.GetLength(1);
     
    // HashMap to store key,value pairs
    Dictionary map = new Dictionary(); 
                                          
    for(int i = 0; i < row; i++)
    {
        for(int j = 0; j < col; j++)
        {
             
            int key = i - j;
             
            // If key value exists in the hashmap,
            if (map.ContainsKey(key))
            {
                 
                // We check whether the current value
                // stored in this key matches to element
                // at current index or not. If not,
                // return false
                if (map[key] != matrix[i, j])
                    return false;
            }
             
            // Else we put key,value pair in hashmap
            else
            {
                map.Add(i - j, matrix[i, j]);
            }
        }
    }
    return true;
}
 
// Driver code   
static void Main()
{
    int[,] matrix = { { 12, 23, -32 },
                      { -20, 12, 23 },
                      { 56, -20, 12 },
                      { 38, 56, -20 } };
    
    // Function call
    string result = (isToeplitz(matrix)) ?
                    "Yes" : "No";
     
    Console.WriteLine(result);
}
}
 
// This code is contributed by divyeshrabadiya07


Javascript


输出
Matrix is a Toeplitz 

解决方案的时间复杂度为 O(n 2 ),因为我们只遍历矩阵中的每个元素一次。
参考: https://en.wikipedia.org/wiki/Toeplitz_matrix

基于散列的方法:

考虑维度 (m, n) 矩阵的索引 (i, j) 处的元素。要使矩阵成为对角常数,对角线上的所有元素必须相同。考虑包含这个 (i, j) 元素的对角线。此对角线中的其他元素将具有 (i+k, j+k) 或 (ik, jk) 形式的索引。请注意,无论这些索引的 x 值和 y 值是什么,它们的差异总是相同的。即 (i+k)-(j+k) == (ik)-(jk) == ij。

下图更好地可视化了这个想法。考虑黄色的对角线。该对角线上任何索引的 x 值和 y 值之差为 2(2-0、3-1、4-2、5-3)。对于所有身体对角线都可以观察到相同的情况。

Toeplitz 矩阵的索引

对于红色对角线,差值为 3。对于绿色对角线,差值为 0。对于橙色对角线,差值为 -2,依此类推……

这个想法是利用这样一个事实,即对于 Toeplitz 矩阵,特定对角线的这些个体索引差异将是唯一的。由于它是一个常数对角矩阵,因此对于所有这些唯一键,应该有与该对角线上的任何元素相同的唯一值。因此,我们创建了一个 HashMap 来存储这些(键、值)对。在任何时候,如果我们遇到一个与它对应的存储键值不同的值,我们就会返回 false。

下面是上述代码的实现:

C++

// C++ program to check whether given
// matrix is a Toeplitz matrix or not
#include 
using namespace std;
 
bool isToeplitz(vector> matrix)
{
     
    // row = number of rows
    // col = number of columns
    int row = matrix.size();
    int col = matrix[0].size();
     
    // HashMap to store key,value pairs
    map Map;
     
    for(int i = 0; i < row; i++)
    {
        for(int j = 0; j < col; j++)
        {
            int key = i - j;
             
            // If key value exists in the hashmap,
            if (Map[key])
            {
                 
                // We check whether the current
                // value stored in this key
                // matches to element at current
                // index or not. If not, return
                // false
                if (Map[key] != matrix[i][j])
                    return false;
            }
             
            // Else we put key,value pair in hashmap
            else
            {
                Map[i - j] = matrix[i][j];
            }
        }
    }
    return true;
}
 
// Driver code
int main()
{
    vector> matrix = { { 12, 23, -32 },
                                   { -20, 12, 23 },
                                   { 56, -20, 12 },
                                   { 38, 56, -20 } };
        
    // Function call
    string result = (isToeplitz(matrix)) ? "Yes" : "No";
     
    cout << result;
     
    return 0;
}
 
// This code is contributed by divyesh072019

Java

// JAVA program to check whether given matrix
// is a Toeplitz matrix or not
 
import java.util.*;
 
class GFG {
 
    static boolean isToeplitz(int[][] matrix)
    {
        // row = number of rows
        // col = number of columns
        int row = matrix.length;
        int col = matrix[0].length;
        // HashMap to store key,value pairs
        HashMap map
            = new HashMap();
        for (int i = 0; i < row; i++)
        {
            for (int j = 0; j < col; j++)
            {
                int key = i - j;
                // if key value exists in the hashmap,
                if (map.containsKey(key))
                {
                    // we check whether the current value
                    // stored in this key matches to element
                    // at current index or not. If not,
                    // return false
                    if (map.get(key) != matrix[i][j])
                        return false;
                }
                // else we put key,value pair in hashmap
                else {
                    map.put(i - j, matrix[i][j]);
                }
            }
        }
        return true;
    }
 
    // Driver Code
    public static void main(String[] args)
    {
        int[][] matrix = { { 12, 23, -32 },
                           { -20, 12, 23 },
                           { 56, -20, 12 },
                           { 38, 56, -20 } };
       
        // Function call
        String result = (isToeplitz(matrix)) ? "Yes" : "No";
        System.out.println(result);
    }
}

Python3

# Python3 program to check whether given matrix
# is a Toeplitz matrix or not
 
def isToeplitz(matrix):
     
    # row = number of rows
    # col = number of columns
    row = len(matrix)
    col = len(matrix[0])
     
    # dictionary to store key,value pairs
    map = {}
    for i in range(row):
        for j in range(col):
            key = i-j
             
            # if key value exists in the map,
            if (key in map):
                 
                # we check whether the current value stored
                # in this key matches to element at current
                # index or not. If not, return false
                if (map[key] != matrix[i][j]):
                    return False
             
            # else we put key,value pair in map
            else:
                map[key] = matrix[i][j]
    return True
 
# Driver Code
if __name__ == "__main__":
    matrix = [[12, 23, -32], [-20, 12, 23], [56, -20, 12], [38, 56, -20]]
     
    # Function call
    if (isToeplitz(matrix)):
        print("Yes")
    else:
        print("No")

C#

// C# program to check whether given
// matrix is a Toeplitz matrix or not
using System;
using System.Collections.Generic;  
 
class GFG{
     
static bool isToeplitz(int[,] matrix)
{
     
    // row = number of rows
    // col = number of columns
    int row = matrix.GetLength(0);
    int col = matrix.GetLength(1);
     
    // HashMap to store key,value pairs
    Dictionary map = new Dictionary(); 
                                          
    for(int i = 0; i < row; i++)
    {
        for(int j = 0; j < col; j++)
        {
             
            int key = i - j;
             
            // If key value exists in the hashmap,
            if (map.ContainsKey(key))
            {
                 
                // We check whether the current value
                // stored in this key matches to element
                // at current index or not. If not,
                // return false
                if (map[key] != matrix[i, j])
                    return false;
            }
             
            // Else we put key,value pair in hashmap
            else
            {
                map.Add(i - j, matrix[i, j]);
            }
        }
    }
    return true;
}
 
// Driver code   
static void Main()
{
    int[,] matrix = { { 12, 23, -32 },
                      { -20, 12, 23 },
                      { 56, -20, 12 },
                      { 38, 56, -20 } };
    
    // Function call
    string result = (isToeplitz(matrix)) ?
                    "Yes" : "No";
     
    Console.WriteLine(result);
}
}
 
// This code is contributed by divyeshrabadiya07

Javascript


输出
Yes

时间复杂度: O(mn) ,其中 m 是行数,n 是列数。
空间复杂度: O(m+n) ,因为在最坏的情况下,如果一个矩阵是 Toeplitz 矩阵,我们正好存储了 (m+n-1) 个键值对。 (在第一行中,我们有 n 个不同的键,然后对于接下来的每 m-1 行,我们不断向映射中添加一个唯一键。