#include <bits/stdc++.h>
using namespace std;
#define ll long long
constexpr const ll MAXN = 500010;
constexpr const ll MOD = 1e9 + 7;
ll n, m;
vector<ll> graph[MAXN];
ll qpow(ll a, ll b, ll p) {
  static ll res;
  res = 1;
  while (b) {
    if (b & 1) res = res * a % p;
    a = a * a % p;
    b >>= 1;
  }
  return res;
}
namespace square_cond{
  
}
namespace tree_cond {
ll siz[MAXN];
ll dp[MAXN][2];
ll ans;
ll dfs(ll u, ll p) {
  siz[u] = 0;
  for (const ll &v : graph[u]) {
    if (v == p) continue;
    dfs(v, u);
    dp[u][0] = (dp[u][0] * qpow(2, siz[v] + 1, MOD) % MOD +
                (dp[v][0] + dp[v][1]) % MOD * qpow(2, siz[u], MOD) % MOD) %
               MOD;
    dp[u][1] = (dp[u][1] * qpow(2, siz[v] + 1, MOD) % MOD +
                dp[u][1] * dp[v][1] % MOD) %
               MOD;
    siz[u] += siz[v];
  }
}
void run() {
  dfs(1, 0);
  cout << ((dp[1][0] + dp[1][1]) % MOD) << endl;
}
}  // namespace tree_cond
int main() {
  ll u, v;
#ifndef DEBUG
  freopen("barrack.in", "r", stdin);
  freopen("barrack.out", "w", stdout);
  ios::sync_with_stdio(false);
  cin.tie(nullptr);
  cout.tie(nullptr);
#endif
  cin >> n >> m;
  for (int i = 1; i <= m; ++i) {
    cin >> u >> v;
    graph[u].emplace_back(v);
    graph[v].emplace_back(u);
  }
  if (m == n - 1) tree_cond::run();
  return 0;
}