N, M = list(map(int, input().split()))

adj_matrix = [[0]* N for _ in range(N)]



for i in range(M):

    a, b = list(map(int, input().split()))

    adj_matrix[a-1][b-1] = 1

    adj_matrix[b-1][a-1] = 1



def dfs(v, used):

    if not False in used:

        return 1

    

    ans = 0

    for i in range(N):

        if not adj_matrix[v][i]:

            continue

        if used[i]:

            continue

        

        used[i] = True

        ans += dfs(i, used)

        used[i] = False

    

    return ans



used = [False] * N

used[0] = True



print((dfs(0, used)))
import bisect

n,m = list(map(int,input().split()))



g = [[ ] for i in range(n+1)]



for i in range(m):

    a,b = list(map(int,input().split()))

    g[a].append(b)

    g[b].append(a)



    #print(bisect.bisect_left(g[a],b))

    #g[a][] = b

    #g[a].append(b)

    #g[b].append(a)



#g[4].sort()

    

ans = 0



def dfs(x,check):

    #print(check,x)

    ans = 0

    if not False in check:

        #print(ans)

        return 1

        #check[x] = 0

        #print(x)

    #print(check)

    for i in g[x]:

        if check[i] == True:

            continue

        #print(i,check)

        check[i] = True

        ans += dfs(i,check)

        check[i] = False

    

    return ans

    

check = [False] * (n+1)

check[0] = True

check[1] = True



print((dfs(1,check)))



N, M = list(map(int, input().split()))
adj_matrix = [[0] * N for _ in range(N)]
for i in range(M):
    a, b = list(map(int, input().split()))
    adj_matrix[a - 1][b - 1] = 1
    adj_matrix[b - 1][a - 1] = 1


def dfs(v, used):
    if not False in used:
        return 1
    ans = 0
    for i in range(N):
        if not adj_matrix[v][i]:
            continue
        if used[i]:
            continue
        used[i] = True
        ans += dfs(i, used)
        used[i] = False
    return ans


used = [False] * N
used[0] = True
print((dfs(0, used)))

import bisect

n, m = list(map(int, input().split()))
g = [[] for i in range(n + 1)]
for i in range(m):
    a, b = list(map(int, input().split()))
    g[a].append(b)
    g[b].append(a)
    # print(bisect.bisect_left(g[a],b))
    # g[a][] = b
    # g[a].append(b)
    # g[b].append(a)
# g[4].sort()
ans = 0


def dfs(x, check):
    # print(check,x)
    ans = 0
    if not False in check:
        # print(ans)
        return 1
        # check[x] = 0
        # print(x)
    # print(check)
    for i in g[x]:
        if check[i] == True:
            continue
        # print(i,check)
        check[i] = True
        ans += dfs(i, check)
        check[i] = False
    return ans


check = [False] * (n + 1)
check[0] = True
check[1] = True
print((dfs(1, check)))

-N, M = list(map(int, input().split())) -adj_matrix = [[0] * N for _ in range(N)] -for i in range(M): +import bisect + +n, m = list(map(int, input().split())) +g = [[] for i in range(n + 1)] +for i in range(m): -    adj_matrix[a - 1][b - 1] = 1 -    adj_matrix[b - 1][a - 1] = 1 +    g[a].append(b) +    g[b].append(a) +    # print(bisect.bisect_left(g[a],b)) +    # g[a][] = b +    # g[a].append(b) +    # g[b].append(a) +# g[4].sort() +ans = 0 -def dfs(v, used): -    if not False in used: +def dfs(x, check): +    # print(check,x) +    ans = 0 +    if not False in check: +        # print(ans) -    ans = 0 -    for i in range(N): -        if not adj_matrix[v][i]: +        # check[x] = 0 +        # print(x) +    # print(check) +    for i in g[x]: +        if check[i] == True: -        if used[i]: -            continue -        used[i] = True -        ans += dfs(i, used) -        used[i] = False +        # print(i,check) +        check[i] = True +        ans += dfs(i, check) +        check[i] = False -used = [False] * N -used[0] = True -print((dfs(0, used))) +check = [False] * (n + 1) +check[0] = True +check[1] = True +print((dfs(1, check)))