They say "years are like dominoes, tumbling one after the other". But would a year fit into a grid? I don't think so.

Limak is a little polar bear who loves to play. He has recently got a rectangular grid with h rows and w columns. Each cell is a square, either empty (denoted by '.') or forbidden (denoted by '#'). Rows are numbered 1 through h from top to bottom. Columns are numbered 1 through w from left to right.

Also, Limak has a single domino. He wants to put it somewhere in a grid. A domino will occupy exactly two adjacent cells, located either in one row or in one column. Both adjacent cells must be empty and must be inside a grid.

Limak needs more fun and thus he is going to consider some queries. In each query he chooses some rectangle and wonders, how many way are there to put a single domino inside of the chosen rectangle?


-----Input-----

The first line of the input contains two integers h and w (1 ≤ h, w ≤ 500) – the number of rows and the number of columns, respectively.

The next h lines describe a grid. Each line contains a string of the length w. Each character is either '.' or '#' — denoting an empty or forbidden cell, respectively.

The next line contains a single integer q (1 ≤ q ≤ 100 000) — the number of queries.

Each of the next q lines contains four integers r1_{i}, c1_{i}, r2_{i}, c2_{i} (1 ≤ r1_{i} ≤ r2_{i} ≤ h, 1 ≤ c1_{i} ≤ c2_{i} ≤ w) — the i-th query. Numbers r1_{i} and c1_{i} denote the row and the column (respectively) of the upper left cell of the rectangle. Numbers r2_{i} and c2_{i} denote the row and the column (respectively) of the bottom right cell of the rectangle.


-----Output-----

Print q integers, i-th should be equal to the number of ways to put a single domino inside the i-th rectangle.


-----Examples-----
Input
5 8
....#..#
.#......
##.#....
##..#.##
........
4
1 1 2 3
4 1 4 1
1 2 4 5
2 5 5 8

Output
4
0
10
15

Input
7 39
.......................................
.###..###..#..###.....###..###..#..###.
...#..#.#..#..#.........#..#.#..#..#...
.###..#.#..#..###.....###..#.#..#..###.
.#....#.#..#....#.....#....#.#..#..#.#.
.###..###..#..###.....###..###..#..###.
.......................................
6
1 1 3 20
2 10 6 30
2 10 7 30
2 2 7 7
1 7 7 7
1 8 7 8

Output
53
89
120
23
0
2



-----Note-----

A red frame below corresponds to the first query of the first sample. A domino can be placed in 4 possible ways. [Image]

Difficulty: MEDIUM
Tags: Dynamic programming

Implementation
Skill types: Dynamic programming

Starter code:

Solutions:
(n, m) = map(int, input().split())
a = []
for _ in range(n):
	x = list(input().strip())
	a.append(x)
hor = [[0 for _ in range(m)] for _ in range(n)]
ver = [[0 for _ in range(m)] for _ in range(n)]
for i in range(n):
	for j in range(m):
		if i - 1 >= 0 and j - 1 >= 0:
			hor[i][j] -= hor[i - 1][j - 1]
			ver[i][j] -= ver[i - 1][j - 1]
		if i - 1 >= 0:
			hor[i][j] += hor[i - 1][j]
			ver[i][j] += ver[i - 1][j]
		if j - 1 >= 0:
			hor[i][j] += hor[i][j - 1]
			ver[i][j] += ver[i][j - 1]
		if j - 1 >= 0 and a[i][j - 1] == '.' and (a[i][j] == '.'):
			hor[i][j] += 1
		if i - 1 >= 0 and a[i - 1][j] == '.' and (a[i][j] == '.'):
			ver[i][j] += 1
q = int(input())
for _ in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	r1 -= 1
	c1 -= 1
	r2 -= 1
	c2 -= 1
	val = hor[r2][c2] + ver[r2][c2]
	val -= hor[r2][c1]
	if r1 - 1 >= 0:
		val += hor[r1 - 1][c1]
		val -= hor[r1 - 1][c2]
	val -= ver[r1][c2]
	if c1 - 1 >= 0:
		val += ver[r1][c1 - 1]
		val -= ver[r2][c1 - 1]
	print(val)


(h, w) = map(int, input().split())
mat = [list(input()) for _ in range(h)]
rows = [[0 for _ in range(w + 1)] for i in range(h + 1)]
cols = [[0 for _ in range(w + 1)] for i in range(h + 1)]
for i in range(h):
	for j in range(1, w):
		rows[i + 1][j + 1] = rows[i + 1][j]
		if mat[i][j] == '.' and mat[i][j - 1] == '.':
			rows[i + 1][j + 1] += 1
for j in range(w):
	for i in range(1, h):
		cols[i + 1][j + 1] = cols[i][j + 1]
		if mat[i][j] == '.' and mat[i - 1][j] == '.':
			cols[i + 1][j + 1] += 1
q = int(input())
for _ in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = 0
	for i in range(r1, r2 + 1):
		ans += rows[i][c2] - rows[i][c1]
	for i in range(c1, c2 + 1):
		ans += cols[r2][i] - cols[r1][i]
	print(ans)


def read_list():
	return [int(i) for i in input().split()]

def new_list(n):
	return [0 for i in range(n)]

def new_matrix(n, m=0):
	return [[0 for i in range(m)] for i in range(n)]
m = 2005
(h, w) = read_list()
d = []
for i in range(h):
	d.append(input())
ver = new_matrix(m, m)
hor = new_matrix(m, m)
for j in range(h):
	for i in range(w):
		hor[i + 1][j + 1] = hor[i + 1][j] + hor[i][j + 1] - hor[i][j]
		ver[i + 1][j + 1] = ver[i + 1][j] + ver[i][j + 1] - ver[i][j]
		if d[j][i] == '.':
			if i < w - 1 and d[j][i + 1] == '.':
				hor[i + 1][j + 1] += 1
			if j < h - 1 and d[j + 1][i] == '.':
				ver[i + 1][j + 1] += 1
n = int(input())
for i in range(n):
	(y1, x1, y2, x2) = read_list()
	x1 -= 1
	y1 -= 1
	answ = 0
	answ += hor[x2 - 1][y2] - hor[x1][y2] - hor[x2 - 1][y1] + hor[x1][y1]
	answ += ver[x2][y2 - 1] - ver[x1][y2 - 1] - ver[x2][y1] + ver[x1][y1]
	print(answ)


read = lambda : map(int, input().split())
(h, w) = read()
a = [input() for i in range(h)]
N = 501
vr = [[0] * N for i in range(N)]
hr = [[0] * N for i in range(N)]
for i in range(h):
	for j in range(w):
		vr[j + 1][i + 1] = vr[j][i + 1] + vr[j + 1][i] - vr[j][i]
		hr[j + 1][i + 1] = hr[j][i + 1] + hr[j + 1][i] - hr[j][i]
		if a[i][j] == '#':
			continue
		if i != h - 1 and a[i + 1][j] == '.':
			vr[j + 1][i + 1] += 1
		if j != w - 1 and a[i][j + 1] == '.':
			hr[j + 1][i + 1] += 1
q = int(input())
for i in range(q):
	(r1, c1, r2, c2) = read()
	p1 = hr[c2 - 1][r2] - hr[c1 - 1][r2] - hr[c2 - 1][r1 - 1] + hr[c1 - 1][r1 - 1]
	p2 = vr[c2][r2 - 1] - vr[c1 - 1][r2 - 1] - vr[c2][r1 - 1] + vr[c1 - 1][r1 - 1]
	ans = p1 + p2
	print(ans)


(n, m) = map(int, input().split())
l = []
for i in range(n):
	l.append(input())
x = [[0 for i in range(m)] for i in range(n)]
y = [[0 for i in range(m)] for i in range(n)]
for i in range(n):
	for j in range(1, m):
		if l[i][j] == '#':
			x[i][j] = x[i][j - 1]
		elif l[i][j - 1] == '.':
			x[i][j] = 1 + x[i][j - 1]
		else:
			x[i][j] = x[i][j - 1]
for i in range(m):
	for j in range(1, n):
		if l[j][i] == '#':
			y[j][i] = y[j - 1][i]
		elif l[j - 1][i] == '.':
			y[j][i] = 1 + y[j - 1][i]
		else:
			y[j][i] = y[j - 1][i]
mod_x = [[0 for i in range(m)] for i in range(n)]
mod_y = [[0 for i in range(m)] for i in range(n)]
for i in range(n):
	for j in range(m):
		if j == 0:
			mod_y[i][j] = y[i][j]
		else:
			mod_y[i][j] += mod_y[i][j - 1] + y[i][j]
for i in range(m):
	for j in range(n):
		if j == 0:
			mod_x[j][i] = x[j][i]
		else:
			mod_x[j][i] += mod_x[j - 1][i] + x[j][i]
q = int(input())
for i in range(q):
	(a, b, c, d) = map(int, input().split())
	a -= 1
	b -= 1
	c -= 1
	d -= 1
	if a == 0:
		ans = mod_x[c][d] - mod_x[c][b]
	else:
		ans = mod_x[c][d] - mod_x[a - 1][d] - mod_x[c][b] + mod_x[a - 1][b]
	if b == 0:
		ans += mod_y[c][d] - mod_y[a][d]
	else:
		ans += mod_y[c][d] - mod_y[c][b - 1] - mod_y[a][d] + mod_y[a][b - 1]
	print(ans)


from math import *

def afft(A):
	for i in range(len(A)):
		ch = ''
		for j in range(len(A[i])):
			if A[i][j] >= 2:
				ch = ch + str(A[i][j]) + ' ' * (3 - int(log(A[i][j], 10)))
			else:
				ch = ch + str(A[i][j]) + '   '
		print(ch)
(h, w) = map(int, input().split())
G = [str(input()) for _ in range(h)]
q = int(input())
L = [list(map(int, input().split())) for _ in range(q)]
H = [[0 for _ in range(w)] for _ in range(h)]
V = [[0 for _ in range(w)] for _ in range(h)]
for i in range(h):
	for j in range(w):
		H[i][j] = H[i][j - 1]
		if j and G[i][j] == '.' and (G[i][j - 1] == '.'):
			H[i][j] += 1
for j in range(w):
	for i in range(h):
		V[i][j] = V[i - 1][j]
		if i and G[i][j] == '.' and (G[i - 1][j] == '.'):
			V[i][j] += 1
for i in range(1, h):
	H[i] = [H[i - 1][j] + H[i][j] for j in range(w)]
for j in range(1, w):
	for i in range(h):
		V[i][j] = V[i][j] + V[i][j - 1]
for Q in L:
	r1 = Q[0] - 1
	c1 = Q[1] - 1
	r2 = Q[2] - 1
	c2 = Q[3] - 1
	if r1 > r2 or c1 > c2:
		print(0)
	else:
		r = H[r2][c2] + V[r2][c2] - H[r2][c1] - V[r1][c2]
		if r1:
			r = r - H[r1 - 1][c2]
		if c1:
			r = r - V[r2][c1 - 1]
		if r1 and c1:
			r = r + H[r1 - 1][c1] + V[r1][c1 - 1]
		print(r)


(h, w) = list(map(int, input().split()))
mp = []
mp.append(list('#' * (w + 2)))
for i in range(h):
	mp.append(list(input()))
	mp[i + 1].insert(0, '#')
	mp[i + 1].append('#')
mp.append(list('#' * (w + 2)))
mpV = []
mpH = []
mpV.append([])
mpH.append([])
for i in range(w + 2):
	mpV[0].append(0)
	mpH[0].append(0)
for i in range(1, h + 2):
	mpV.append([])
	mpH.append([])
	mpV[i].append(0)
	mpH[i].append(0)
	for j in range(1, w + 2):
		mpV[i].append(mpV[i][j - 1] + mpV[i - 1][j] - mpV[i - 1][j - 1] + (1 if mp[i][j] == '.' and mp[i + 1][j] == '.' else 0))
		mpH[i].append(mpH[i][j - 1] + mpH[i - 1][j] - mpH[i - 1][j - 1] + (1 if mp[i][j] == '.' and mp[i][j + 1] == '.' else 0))
anc = []
n = int(input())
for k in range(n):
	(y0, x0, y1, x1) = list(map(int, input().split()))
	A = mpV[y0 - 1][x0 - 1] + mpV[y1 - 1][x1] - mpV[y1 - 1][x0 - 1] - mpV[y0 - 1][x1]
	A += mpH[y0 - 1][x0 - 1] + mpH[y1][x1 - 1] - mpH[y1][x0 - 1] - mpH[y0 - 1][x1 - 1]
	anc.append(A)
for k in range(n):
	print(anc[k])


(h, w) = map(int, input().split())
s = []
for i in range(h):
	s.append(list(input()))
	s[i].append('#')
s.append(['#'] * (w + 1))
v = [[0] * (w + 2)]
g = [[0] * (w + 2)]
for i in range(h + 1):
	v.append([0] * (w + 2))
	g.append([0] * (w + 2))
for i in range(len(s)):
	count = 0
	for j in range(1, len(s[0])):
		if s[i][j] == '.' and s[i][j - 1] == '.':
			count += 1
		if i == 0:
			g[i][j] = count
		else:
			g[i][j] = count + g[i - 1][j]
for j in range(len(s[0])):
	count = 0
	for i in range(1, len(s)):
		if s[i][j] == '.' and s[i - 1][j] == '.':
			count += 1
		if j == 0:
			v[i][j] = count
		else:
			v[i][j] = count + v[i][j - 1]
q = int(input())
g = g[:h]
g.insert(0, [0] * (w + 1))
for i in range(len(g)):
	g[i] = g[i][:w]
	g[i].insert(0, 0)
v = v[:h]
v.insert(0, [0] * (w + 1))
for i in range(len(v)):
	v[i] = v[i][:w]
	v[i].insert(0, 0)
for i in range(q):
	count = 0
	(u1, u2, d1, d2) = map(int, input().split())
	if u1 == d1 and d2 == u2:
		print(0)
		continue
	count += g[d1][d2]
	count -= g[d1][u2]
	count -= g[u1 - 1][d2]
	count += g[u1 - 1][u2]
	count += v[d1][d2]
	count -= v[d1][u2 - 1]
	count -= v[u1][d2]
	count += v[u1][u2 - 1]
	print(count)


(h, w) = map(int, input().split())
lt = [[0 for _ in range(600)] for _ in range(600)]
for i in range(1, h + 1):
	s = '0' + input()
	for j in range(1, w + 1):
		lt[i][j] = s[j]
(dp1, dp2) = ([[0 for _ in range(600)] for _ in range(600)], [[0 for _ in range(600)] for _ in range(600)])
for i in range(1, h + 1):
	for j in range(1, w + 1):
		dp1[i][j] = dp1[i - 1][j] + dp1[i][j - 1] - dp1[i - 1][j - 1] + (lt[i][j] == lt[i][j - 1] == '.')
		dp2[i][j] = dp2[i - 1][j] + dp2[i][j - 1] - dp2[i - 1][j - 1] + (lt[i][j] == lt[i - 1][j] == '.')
q = int(input())
for _ in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = 0
	ans += dp1[r2][c2] - dp1[r1 - 1][c2] - dp1[r2][c1] + dp1[r1 - 1][c1]
	ans += dp2[r2][c2] - dp2[r1][c2] - dp2[r2][c1 - 1] + dp2[r1][c1 - 1]
	print(ans)


import os, sys
from io import BytesIO, IOBase
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
from math import ceil
mod = 10 ** 9 + 7
for _ in range(1):
	(n, m) = map(int, input().split())
	matrix = []
	prefix_row_matrix = [[0 for i in range(m)] for j in range(n)]
	for i in range(n):
		l = input()
		matrix.append(l)
		spaces = 0
		for j in range(m):
			if l[j] == '#':
				spaces = 0
				if j == 0:
					prefix_row_matrix[i][j] = 0
				else:
					prefix_row_matrix[i][j] += prefix_row_matrix[i][j - 1]
			elif l[j] == '.':
				spaces += 1
				if spaces >= 2:
					prefix_row_matrix[i][j] += prefix_row_matrix[i][j - 1] + 1
				elif j == 0:
					prefix_row_matrix[i][j] = 0
				else:
					prefix_row_matrix[i][j] += prefix_row_matrix[i][j - 1]
	prefix_col_matrix = [[0 for i in range(n)] for j in range(m)]
	for j in range(m):
		spaces = 0
		for i in range(n):
			if matrix[i][j] == '#':
				spaces = 0
				if i == 0:
					prefix_col_matrix[j][i] = 0
				else:
					prefix_col_matrix[j][i] += prefix_col_matrix[j][i - 1]
			elif matrix[i][j] == '.':
				spaces += 1
				if spaces >= 2:
					prefix_col_matrix[j][i] += prefix_col_matrix[j][i - 1] + 1
				elif i == 0:
					prefix_col_matrix[j][i] = 0
				else:
					prefix_col_matrix[j][i] += prefix_col_matrix[j][i - 1]
	for q in range(int(input())):
		(x1, y1, x2, y2) = map(int, input().split())
		total_ways = 0
		for col in range(y1 - 1, y2):
			total_ways += abs(prefix_col_matrix[col][x1 - 1] - prefix_col_matrix[col][x2 - 1])
		for row in range(x1 - 1, x2):
			total_ways += abs(prefix_row_matrix[row][y1 - 1] - prefix_row_matrix[row][y2 - 1])
		print(total_ways)


(n, m) = map(int, input().split())
a = []
for i in range(n):
	s = input()
	tmp = list(s)
	a.append(tmp)
right = []
up = []
for i in range(n):
	tmp1 = []
	tmp2 = []
	for j in range(m):
		tmp1.append(0)
		tmp2.append(0)
	right.append(tmp1)
	up.append(tmp2)
for i in range(1, m):
	if a[0][i] == '#':
		right[0][i] = right[0][i - 1]
	elif a[0][i - 1] == '.':
		right[0][i] = 1 + right[0][i - 1]
	else:
		right[0][i] = right[0][i - 1]
for i in range(1, n):
	if a[i][0] == '#':
		up[i][0] = up[i - 1][0]
	elif a[i - 1][0] == '.':
		up[i][0] = 1 + up[i - 1][0]
	else:
		up[i][0] = up[i - 1][0]
for i in range(1, n):
	for j in range(1, m):
		if a[i][j] == '#':
			right[i][j] = right[i - 1][j] + right[i][j - 1] - right[i - 1][j - 1]
			up[i][j] = up[i - 1][j] + up[i][j - 1] - up[i - 1][j - 1]
		else:
			if a[i][j - 1] == '.':
				right[i][j] = 1 + right[i - 1][j] + right[i][j - 1] - right[i - 1][j - 1]
			else:
				right[i][j] = right[i - 1][j] + right[i][j - 1] - right[i - 1][j - 1]
			if a[i - 1][j] == '.':
				up[i][j] = up[i - 1][j] + up[i][j - 1] - up[i - 1][j - 1] + 1
			else:
				up[i][j] = up[i - 1][j] + up[i][j - 1] - up[i - 1][j - 1]
q = int(input())
for _ in range(q):
	(i1, j1, i2, j2) = map(int, input().split())
	i1 -= 1
	j1 -= 1
	i2 -= 1
	j2 -= 1
	if i1 > 0:
		ans = right[i2][j2] - right[i2][j1] - right[i1 - 1][j2] + right[i1 - 1][j1]
	else:
		ans = right[i2][j2] - right[i2][j1]
	if j1 > 0:
		ans += up[i2][j2] - up[i2][j1 - 1] - up[i1][j2] + up[i1][j1 - 1]
	else:
		ans += up[i2][j2] - up[i1][j2]
	print(ans)


(h, w) = map(int, input().split())
t = []
for i in range(h):
	lis = input()
	t.append(lis)
a = [[0 for i in range(w)] for j in range(h)]
for i in range(h):
	maxi = 0
	for j in range(1, w):
		if t[i][j] == '.' == t[i][j - 1]:
			a[i][j] = maxi + 1
			maxi = max(maxi, a[i][j])
		else:
			a[i][j] = maxi
d = [[0 for i in range(w)] for j in range(h)]
for i in range(w):
	d[0][i] = a[0][i]
for i in range(1, h):
	for j in range(w):
		d[i][j] = d[i - 1][j] + a[i][j]
a = [[0 for i in range(w)] for j in range(h)]
for j in range(w):
	maxi = 0
	for i in range(1, h):
		if t[i][j] == '.' == t[i - 1][j]:
			a[i][j] = maxi + 1
			maxi = max(maxi, a[i][j])
		else:
			a[i][j] = maxi
d1 = [[0 for i in range(w)] for j in range(h)]
for i in range(h):
	d1[i][0] = a[i][0]
for j in range(1, w):
	for i in range(h):
		d1[i][j] = a[i][j] + d1[i][j - 1]
q = int(input())
for i in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	r1 -= 1
	c1 -= 1
	r2 -= 1
	c2 -= 1
	if r1 == 0 and c1 == 0:
		print(d[r2][c2] + d1[r2][c2])
	elif r1 == 0:
		print(d[r2][c2] + d1[r2][c2] - d[r2][c1] - d1[r2][c1 - 1])
	elif c1 == 0:
		print(d[r2][c2] + d1[r2][c2] - d[r1 - 1][c2] - d1[r1][c2])
	else:
		print(d[r2][c2] + d1[r2][c2] - d[r1 - 1][c2] - d1[r1][c2] - d[r2][c1] - d1[r2][c1 - 1] + d[r1 - 1][c1] + d1[r1][c1 - 1])


(h, w) = [int(e) for e in input().split()]
a = [['#' for _ in range(w + 2)] for _ in range(h + 2)]
hor = [[0 for _ in range(w + 2)] for _ in range(h + 2)]
ver = [[0 for _ in range(w + 2)] for _ in range(h + 2)]
for i in range(1, h + 1):
	a[i] = ['#'] + list(input()) + ['#']
for i in range(1, h + 1):
	for j in range(1, w + 1):
		hor[i][j] = hor[i - 1][j] + hor[i][j - 1] - hor[i - 1][j - 1]
		ver[i][j] = ver[i - 1][j] + ver[i][j - 1] - ver[i - 1][j - 1]
		if a[i][j] == '.' and a[i][j - 1] == '.':
			hor[i][j] += 1
		if a[i][j] == '.' and a[i - 1][j] == '.':
			ver[i][j] += 1
q = int(input())
for _ in range(q):
	(r1, c1, r2, c2) = [int(e) for e in input().split()]
	ans = 0
	ans += hor[r2][c2] - hor[r1 - 1][c2] - hor[r2][c1] + hor[r1 - 1][c1]
	ans += ver[r2][c2] - ver[r1][c2] - ver[r2][c1 - 1] + ver[r1][c1 - 1]
	print(ans)


from itertools import accumulate
import math
import bisect

def list_sum(L1, L2):
	return [L1[i] + L2[i] for i in range(len(L1))]
(h, w) = [int(x) for x in input().split()]
M = []
for i in range(h):
	M.append([1 if c == '.' else 0 for c in input().rstrip()])
H = [[0] + list(accumulate((M[i][j] and M[i][j + 1] for j in range(w - 1)))) for i in range(h)]
V = [[0] + list(accumulate((M[i][j] and M[i + 1][j] for i in range(h - 1)))) for j in range(w)]
Hsum = list(accumulate(H, list_sum))
Vsum = list(accumulate(V, list_sum))

def can(a, b):
	return Hsum[a][b] + Vsum[b][a]

def query(a1, b1, a2, b2):
	return can(a2, b2) + can(a1, b1) - can(a1, b2) - can(a2, b1) + H[a1][b2] - H[a1][b1] + V[b1][a2] - V[b1][a1]
q = int(input())
for i in range(q):
	(a1, b1, a2, b2) = [int(x) - 1 for x in input().split()]
	print(query(a1, b1, a2, b2))


import sys
input = sys.stdin.readline
(n, m) = map(int, input().split())
matrix = [list(input().strip()) for _ in range(n)]
h = [[0 for _ in range(m)] for _ in range(n)]
v = [[0 for _ in range(m)] for _ in range(n)]
for i in range(n):
	for j in range(1, m):
		h[i][j] = h[i][j - 1] + (matrix[i][j] == '.' and matrix[i][j - 1] == '.') * 1
for i in range(1, n):
	for j in range(m):
		v[i][j] = v[i - 1][j] + (matrix[i][j] == '.' and matrix[i - 1][j] == '.') * 1
for i in range(int(input())):
	(a, b, c, d) = map(int, input().split())
	ans = 0
	for x in range(a - 1, c):
		ans += h[x][d - 1] - h[x][b - 1]
	for x in range(b - 1, d):
		ans += v[c - 1][x] - v[a - 1][x]
	print(ans)


(n, m) = map(int, input().split())
s = ['#' * (m + 2)]
for i in range(n):
	s += ['#' + input() + '#']
s += ['#' * (m + 2)]
u = [[0 for i in range(m + 2)] for j in range(n + 2)]
r = [[0 for i in range(m + 2)] for j in range(n + 2)]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		if s[i][j] == '.':
			if s[i + 1][j] == '.':
				u[i][j] = 1
			if s[i][j + 1] == '.':
				r[i][j] = 1
		u[i][j] += u[i - 1][j] + u[i][j - 1] - u[i - 1][j - 1]
		r[i][j] += r[i - 1][j] + r[i][j - 1] - r[i - 1][j - 1]
q = int(input())
for i in range(q):
	A = 0
	(x, y, a, b) = map(int, input().split())
	if x == a and y == b:
		A = 0
	else:
		A += r[a][b - 1] - r[x - 1][b - 1] - r[a][y - 1] + r[x - 1][y - 1]
		A += u[a - 1][b] - u[x - 1][b] - u[a - 1][y - 1] + u[x - 1][y - 1]
	print(A)


(h, w) = map(int, input().split())
field = [input() for i in range(h)]
q = int(input())
inrow = [[0] * (w + 1) for i in range(h + 1)]
for i in range(h):
	sum = 0
	for j in range(1, w):
		if field[i][j] == field[i][j - 1] == '.':
			sum += 1
		inrow[i][j] = sum
incol = [[0] * (h + 1) for i in range(w + 1)]
for j in range(w):
	sum = 0
	for i in range(1, h):
		if field[i][j] == field[i - 1][j] == '.':
			sum += 1
		incol[j][i] = sum
suminrows = [[0] * (w + 1) for i in range(h + 1)]
for j in range(w):
	sum = 0
	for i in range(h):
		sum += inrow[i][j]
		suminrows[i][j] = sum
sumincols = [[0] * (h + 1) for i in range(w + 1)]
for i in range(h):
	sum = 0
	for j in range(w):
		sum += incol[j][i]
		sumincols[j][i] = sum
for test in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	(r1, c1, r2, c2) = (r1 - 1, c1 - 1, r2 - 1, c2 - 1)
	ans = 0
	ans += suminrows[r2][c2] - suminrows[r1 - 1][c2] - (suminrows[r2][c1] - suminrows[r1 - 1][c1])
	ans += sumincols[c2][r2] - sumincols[c1 - 1][r2] - (sumincols[c2][r1] - sumincols[c1 - 1][r1])
	print(ans)


__author__ = 'Utena'
(h, w) = map(int, input().split())
q = [[0] * w for i in range(h)]
for i1 in range(h):
	n0 = input()
	for i in range(w):
		if n0[i] == '#':
			q[i1][i] = 1
a = [[0] * w for i2 in range(h + 1)]
b = [[0] * (w + 1) for i3 in range(h)]
for i in range(h):
	for j in range(w - 1):
		if q[i][j] == q[i][j + 1] == 0:
			a[i + 1][j + 1] = a[i + 1][j] + 1
		else:
			a[i + 1][j + 1] = a[i + 1][j]
for i in range(1, h + 1):
	for j in range(w):
		a[i][j] += a[i - 1][j]
for i in range(h - 1):
	for j in range(w):
		if q[i][j] == q[i + 1][j] == 0:
			b[i + 1][j + 1] = b[i][j + 1] + 1
		else:
			b[i + 1][j + 1] = b[i][j + 1]
for i in range(h):
	for j in range(1, w + 1):
		b[i][j] += b[i][j - 1]
n = int(input())
for k in range(n):
	(r1, c1, r2, c2) = list(map(int, input().split()))
	t = a[r2][c2 - 1] - a[r2][c1 - 1] - a[r1 - 1][c2 - 1] + a[r1 - 1][c1 - 1] + b[r2 - 1][c2] - b[r1 - 1][c2] - b[r2 - 1][c1 - 1] + b[r1 - 1][c1 - 1]
	print(t)


(h, w) = list(map(int, input().split()))
grid = (h + 1) * [None]
grid[0] = (w + 1) * '#'
for r in range(1, h + 1):
	grid[r] = '#' + input().strip()
rt = [[0 for c in range(w + 1)] for r in range(h + 1)]
for r in range(1, h + 1):
	for c in range(1, w + 1):
		if '.' == grid[r][c] == grid[r][c - 1]:
			delta = 1
		else:
			delta = 0
		rt[r][c] = rt[r][c - 1] + delta
	for c in range(1, w + 1):
		rt[r][c] += rt[r - 1][c]
ct = [[0 for c in range(w + 1)] for r in range(h + 1)]
for c in range(1, w + 1):
	for r in range(1, h + 1):
		if '.' == grid[r][c] == grid[r - 1][c]:
			delta = 1
		else:
			delta = 0
		ct[r][c] = ct[r - 1][c] + delta
	for r in range(1, h + 1):
		ct[r][c] += ct[r][c - 1]
debug = False
if debug:
	print()
	for r in range(1, h + 1):
		print(grid[r][1:])
		print(rt[r][1:])
	print()
	for c in range(1, w + 1):
		print(''.join([grid[r][c] for r in range(1, h + 1)]))
		print([ct[r][c] for r in range(1, h + 1)])
	print()
q = int(input())
for i in range(q):
	(r, c, R, C) = list(map(int, input().split()))
	if debug:
		print((rt[R][C], -rt[R][c], -rt[r - 1][C], rt[r - 1][c], '\n', ct[R][C], -ct[r][C], -ct[R][c - 1], ct[r][c - 1]))
	x = rt[R][C] - rt[R][c] - rt[r - 1][C] + rt[r - 1][c] + ct[R][C] - ct[r][C] - ct[R][c - 1] + ct[r][c - 1]
	print(x)


import sys, os, io

def rs():
	return sys.stdin.readline().rstrip()

def ri():
	return int(sys.stdin.readline())

def ria():
	return list(map(int, sys.stdin.readline().split()))

def ws(s):
	sys.stdout.write(s + '\n')

def wi(n):
	sys.stdout.write(str(n) + '\n')

def wia(a):
	sys.stdout.write(' '.join([str(x) for x in a]) + '\n')
import math, datetime, functools, itertools, operator, bisect, fractions, statistics
from collections import deque, defaultdict, OrderedDict, Counter
from fractions import Fraction
from decimal import Decimal
from sys import stdout
from heapq import heappush, heappop, heapify, _heapify_max, _heappop_max, nsmallest, nlargest
sys.setrecursionlimit(111111)
INF = 999999999999999999999999

class SortedList:

	def __init__(self, iterable=[], _load=200):
		values = sorted(iterable)
		self._len = _len = len(values)
		self._load = _load
		self._lists = _lists = [values[i:i + _load] for i in range(0, _len, _load)]
		self._list_lens = [len(_list) for _list in _lists]
		self._mins = [_list[0] for _list in _lists]
		self._fen_tree = []
		self._rebuild = True

	def _fen_build(self):
		self._fen_tree[:] = self._list_lens
		_fen_tree = self._fen_tree
		for i in range(len(_fen_tree)):
			if i | i + 1 < len(_fen_tree):
				_fen_tree[i | i + 1] += _fen_tree[i]
		self._rebuild = False

	def _fen_update(self, index, value):
		if not self._rebuild:
			_fen_tree = self._fen_tree
			while index < len(_fen_tree):
				_fen_tree[index] += value
				index |= index + 1

	def _fen_query(self, end):
		if self._rebuild:
			self._fen_build()
		_fen_tree = self._fen_tree
		x = 0
		while end:
			x += _fen_tree[end - 1]
			end &= end - 1
		return x

	def _fen_findkth(self, k):
		_list_lens = self._list_lens
		if k < _list_lens[0]:
			return (0, k)
		if k >= self._len - _list_lens[-1]:
			return (len(_list_lens) - 1, k + _list_lens[-1] - self._len)
		if self._rebuild:
			self._fen_build()
		_fen_tree = self._fen_tree
		idx = -1
		for d in reversed(range(len(_fen_tree).bit_length())):
			right_idx = idx + (1 << d)
			if right_idx < len(_fen_tree) and k >= _fen_tree[right_idx]:
				idx = right_idx
				k -= _fen_tree[idx]
		return (idx + 1, k)

	def _delete(self, pos, idx):
		_lists = self._lists
		_mins = self._mins
		_list_lens = self._list_lens
		self._len -= 1
		self._fen_update(pos, -1)
		del _lists[pos][idx]
		_list_lens[pos] -= 1
		if _list_lens[pos]:
			_mins[pos] = _lists[pos][0]
		else:
			del _lists[pos]
			del _list_lens[pos]
			del _mins[pos]
			self._rebuild = True

	def _loc_left(self, value):
		if not self._len:
			return (0, 0)
		_lists = self._lists
		_mins = self._mins
		(lo, pos) = (-1, len(_lists) - 1)
		while lo + 1 < pos:
			mi = lo + pos >> 1
			if value <= _mins[mi]:
				pos = mi
			else:
				lo = mi
		if pos and value <= _lists[pos - 1][-1]:
			pos -= 1
		_list = _lists[pos]
		(lo, idx) = (-1, len(_list))
		while lo + 1 < idx:
			mi = lo + idx >> 1
			if value <= _list[mi]:
				idx = mi
			else:
				lo = mi
		return (pos, idx)

	def _loc_right(self, value):
		if not self._len:
			return (0, 0)
		_lists = self._lists
		_mins = self._mins
		(pos, hi) = (0, len(_lists))
		while pos + 1 < hi:
			mi = pos + hi >> 1
			if value < _mins[mi]:
				hi = mi
			else:
				pos = mi
		_list = _lists[pos]
		(lo, idx) = (-1, len(_list))
		while lo + 1 < idx:
			mi = lo + idx >> 1
			if value < _list[mi]:
				idx = mi
			else:
				lo = mi
		return (pos, idx)

	def add(self, value):
		_load = self._load
		_lists = self._lists
		_mins = self._mins
		_list_lens = self._list_lens
		self._len += 1
		if _lists:
			(pos, idx) = self._loc_right(value)
			self._fen_update(pos, 1)
			_list = _lists[pos]
			_list.insert(idx, value)
			_list_lens[pos] += 1
			_mins[pos] = _list[0]
			if _load + _load < len(_list):
				_lists.insert(pos + 1, _list[_load:])
				_list_lens.insert(pos + 1, len(_list) - _load)
				_mins.insert(pos + 1, _list[_load])
				_list_lens[pos] = _load
				del _list[_load:]
				self._rebuild = True
		else:
			_lists.append([value])
			_mins.append(value)
			_list_lens.append(1)
			self._rebuild = True

	def discard(self, value):
		_lists = self._lists
		if _lists:
			(pos, idx) = self._loc_right(value)
			if idx and _lists[pos][idx - 1] == value:
				self._delete(pos, idx - 1)

	def remove(self, value):
		_len = self._len
		self.discard(value)
		if _len == self._len:
			raise ValueError('{0!r} not in list'.format(value))

	def pop(self, index=-1):
		(pos, idx) = self._fen_findkth(self._len + index if index < 0 else index)
		value = self._lists[pos][idx]
		self._delete(pos, idx)
		return value

	def bisect_left(self, value):
		(pos, idx) = self._loc_left(value)
		return self._fen_query(pos) + idx

	def bisect_right(self, value):
		(pos, idx) = self._loc_right(value)
		return self._fen_query(pos) + idx

	def count(self, value):
		return self.bisect_right(value) - self.bisect_left(value)

	def __len__(self):
		return self._len

	def __getitem__(self, index):
		(pos, idx) = self._fen_findkth(self._len + index if index < 0 else index)
		return self._lists[pos][idx]

	def __delitem__(self, index):
		(pos, idx) = self._fen_findkth(self._len + index if index < 0 else index)
		self._delete(pos, idx)

	def __contains__(self, value):
		_lists = self._lists
		if _lists:
			(pos, idx) = self._loc_left(value)
			return idx < len(_lists[pos]) and _lists[pos][idx] == value
		return False

	def __iter__(self):
		return (value for _list in self._lists for value in _list)

	def __reversed__(self):
		return (value for _list in reversed(self._lists) for value in reversed(_list))

	def __repr__(self):
		return 'SortedList({0})'.format(list(self))

def main():
	mod = 1000000007
	starttime = datetime.datetime.now()
	if os.path.exists('input.txt'):
		sys.stdin = open('input.txt', 'r')
		sys.stdout = open('output.txt', 'w')
	tc = 1
	for _ in range(tc):
		(n, m) = ria()
		matrix = []
		for i in range(n):
			matrix.append(list(rs()))
		q = ri()
		rowcalc = []
		colcalc = []
		for i in range(n):
			p = 0
			z = [0]
			for j in range(1, m):
				if matrix[i][j] == '.':
					if matrix[i][j - 1] == '.':
						p += 1
				z.append(p)
			rowcalc.append(z)
		for j in range(m):
			p = 0
			z = [0]
			for i in range(1, n):
				if matrix[i][j] == '.':
					if matrix[i - 1][j] == '.':
						p += 1
				z.append(p)
			colcalc.append(z)
		for i in range(q):
			ans = 0
			(r1, c1, r2, c2) = ria()
			for j in range(r1 - 1, r2):
				ans += rowcalc[j][c2 - 1] - rowcalc[j][c1 - 1]
			for j in range(c1 - 1, c2):
				ans += colcalc[j][r2 - 1] - colcalc[j][r1 - 1]
			wi(ans)
	endtime = datetime.datetime.now()
	time = (endtime - starttime).total_seconds() * 1000
	if os.path.exists('input.txt'):
		print('Time:', time, 'ms')

class FastReader(io.IOBase):
	newlines = 0

	def __init__(self, fd, chunk_size=1024 * 8):
		self._fd = fd
		self._chunk_size = chunk_size
		self.buffer = io.BytesIO()

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, self._chunk_size))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self, size=-1):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, self._chunk_size if size == -1 else size))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

class FastWriter(io.IOBase):

	def __init__(self, fd):
		self._fd = fd
		self.buffer = io.BytesIO()
		self.write = self.buffer.write

	def flush(self):
		os.write(self._fd, self.buffer.getvalue())
		(self.buffer.truncate(0), self.buffer.seek(0))

class FastStdin(io.IOBase):

	def __init__(self, fd=0):
		self.buffer = FastReader(fd)
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')

class FastStdout(io.IOBase):

	def __init__(self, fd=1):
		self.buffer = FastWriter(fd)
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.flush = self.buffer.flush
sys.stdin = FastStdin()
sys.stdout = FastStdout()
main()


(h, w) = (int(x) for x in input().split())
a = [[x != '.' for x in input()] for _ in range(h)]

def build(f):
	d = [[0 for _ in range(w + 1)]]
	for r in range(h):
		d.append([0])
		for c in range(w):
			d[-1].append(d[-2][c + 1] + d[-1][c] - d[-2][c] + f(r, c))
	return d
ver = build(lambda r, c: not a[r][c] and r < h - 1 and (not a[r + 1][c]))
hor = build(lambda r, c: not a[r][c] and c < w - 1 and (not a[r][c + 1]))
for _ in range(int(input())):
	(r1, c1, r2, c2) = (int(x) for x in input().split())
	s = ver[r2 - 1][c2] - ver[r1 - 1][c2] - ver[r2 - 1][c1 - 1] + ver[r1 - 1][c1 - 1]
	s += hor[r2][c2 - 1] - hor[r1 - 1][c2 - 1] - hor[r2][c1 - 1] + hor[r1 - 1][c1 - 1]
	print(s)


(H, W) = list(map(int, input().split()))
grid = ['|' * (W + 1)] + ['|' + input() for _ in range(H)]
Q = int(input())
hor = [[0 for _ in range(W + 1)] for _ in range(H + 1)]
ver = [[0 for _ in range(W + 1)] for _ in range(H + 1)]
for i in range(1, H + 1):
	for j in range(1, W + 1):
		hor[i][j] = hor[i - 1][j] + hor[i][j - 1] - hor[i - 1][j - 1]
		ver[i][j] = ver[i - 1][j] + ver[i][j - 1] - ver[i - 1][j - 1]
		if grid[i][j - 1] == '.' and grid[i][j] == '.':
			hor[i][j] += 1
		if grid[i - 1][j] == '.' and grid[i][j] == '.':
			ver[i][j] += 1
for _ in range(Q):
	(r1, c1, r2, c2) = list(map(int, input().split()))
	answer = 0
	answer += ver[r2][c2] - ver[r1][c2] - ver[r2][c1 - 1] + ver[r1][c1 - 1]
	answer += hor[r2][c2] - hor[r2][c1] - hor[r1 - 1][c2] + hor[r1 - 1][c1]
	print(answer)


line = input().split()
(h, w) = (int(line[0]), int(line[1]))
grid = []
for i in range(0, h):
	line = input()
	grid.append(line)
q = int(input().split()[0])
dp = [[[0 for z in range(0, 2)] for x in range(w)] for y in range(h)]
for i in range(0, h):
	for j in range(0, w):
		dp[i][j][0] += (dp[i - 1][j][0] if i > 0 else 0) + (dp[i][j - 1][0] if j > 0 else 0) - (dp[i - 1][j - 1][0] if i > 0 and j > 0 else 0)
		dp[i][j][1] += (dp[i - 1][j][1] if i > 0 else 0) + (dp[i][j - 1][1] if j > 0 else 0) - (dp[i - 1][j - 1][1] if i > 0 and j > 0 else 0)
		dp[i][j][0] += 1 if i > 0 and grid[i][j] == '.' and (grid[i - 1][j] == '.') else 0
		dp[i][j][1] += 1 if j > 0 and grid[i][j] == '.' and (grid[i][j - 1] == '.') else 0
while q > 0:
	line = input().split()
	(r1, c1, r2, c2) = (int(line[0]), int(line[1]), int(line[2]), int(line[3]))
	r1 -= 1
	c1 -= 1
	r2 -= 1
	c2 -= 1
	ans = 0
	ans += dp[r2][c2][0] + dp[r2][c2][1]
	ans -= dp[r1 - 1][c2][0] + dp[r1 - 1][c2][1] if r1 > 0 else 0
	ans -= dp[r2][c1 - 1][0] + dp[r2][c1 - 1][1] if c1 > 0 else 0
	ans += dp[r1 - 1][c1 - 1][0] + dp[r1 - 1][c1 - 1][1] if r1 > 0 and c1 > 0 else 0
	ans -= dp[r1][c2][0] - (dp[r1 - 1][c2][0] if r1 > 0 else 0) - (dp[r1][c1 - 1][0] if c1 > 0 else 0) + (dp[r1 - 1][c1 - 1][0] if c1 > 0 and r1 > 0 else 0)
	ans -= dp[r2][c1][1] - (dp[r2][c1 - 1][1] if c1 > 0 else 0) - (dp[r1 - 1][c1][1] if r1 > 0 else 0) + (dp[r1 - 1][c1 - 1][1] if c1 > 0 and r1 > 0 else 0)
	print(ans)
	q -= 1


from collections import defaultdict, Counter
import os
import sys
from io import BytesIO, IOBase
ii = lambda : int(input())
lmii = lambda : list(map(int, input().split()))
slmii = lambda : sorted(map(int, input().split()))
li = lambda : list(input())
mii = lambda : map(int, input().split())
msi = lambda : map(str, input().split())

def gcd(a, b):
	if b == 0:
		return a
	return gcd(b, a % b)

def lcm(a, b):
	return a * b // gcd(a, b)

def main():
	(h, w) = mii()
	a = []
	for i in range(h):
		a.append(li())
	row = []
	col = []
	for i in range(h):
		rlst = []
		clst = []
		for j in range(w):
			if j == 0:
				rlst.append(0)
			else:
				rlst.append(rlst[-1] + (a[i][j] == '.' and a[i][j - 1] == '.'))
			if i == 0:
				clst.append(0)
			else:
				clst.append(col[-1][j] + (a[i][j] == '.' and a[i - 1][j] == '.'))
		row.append(rlst)
		col.append(clst)
	q = ii()
	for i in range(q):
		(r1, c1, r2, c2) = mii()
		cnt = 0
		for j in range(c1, c2 + 1):
			cnt += col[r2 - 1][j - 1]
		for j in range(r1, r2 + 1):
			cnt += row[j - 1][c2 - 1]
		for j in range(r1, r2 + 1):
			cnt -= row[j - 1][c1 - 1]
		for j in range(c1, c2 + 1):
			cnt -= col[r1 - 1][j - 1]
		print(cnt)
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
main()


def lol(i):
	return int(i) - 1
(h, w) = map(int, input().split())
a = []
for _ in range(h):
	a.append(input())
hor = [[0] * (w + 1) for i in range(h + 1)]
ver = [[0] * (w + 1) for i in range(h + 1)]
for y in range(0, h):
	for x in range(0, w):
		hor[y + 1][x + 1] = hor[y + 1][x] + hor[y][x + 1] - hor[y][x]
		ver[y + 1][x + 1] = ver[y + 1][x] + ver[y][x + 1] - ver[y][x]
		if a[y][x] == '.':
			if x < w - 1 and a[y][x + 1] == '.':
				hor[y + 1][x + 1] += 1
			if y < h - 1 and a[y + 1][x] == '.':
				ver[y + 1][x + 1] += 1
t = int(input())
for _ in range(t):
	(y1, x1, y2, x2) = map(int, input().split())
	x1 -= 1
	y1 -= 1
	ans = 0
	ans += hor[y2][x2 - 1] - hor[y2][x1] - hor[y1][x2 - 1] + hor[y1][x1]
	ans += ver[y2 - 1][x2] - ver[y2 - 1][x1] - ver[y1][x2] + ver[y1][x1]
	print(ans)


import sys
import os
from io import BytesIO, IOBase

def cel(n, k):
	return n // k + (n % k != 0)

def ii():
	return int(input())

def mi():
	return map(int, input().split())

def li():
	return list(map(int, input().split()))

def lcm(a, b):
	return abs(a * b) // math.gcd(a, b)

def prr(a, sep=' '):
	print(sep.join(map(str, a)))

def dd():
	return defaultdict(int)

def ddl():
	return defaultdict(list)

def ddd():
	return defaultdict(defaultdict(int))
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
from collections import defaultdict
(h, w) = mi()
a = ['#' * (w + 1)]
for i in range(h):
	a.append('#' + input())
dp_h = [[0 for i in range(w + 1)] for j in range(h + 1)]
dp_v = [[0 for i in range(w + 1)] for j in range(h + 1)]
for i in range(1, h + 1):
	for j in range(1, w + 1):
		dp_h[i][j] = dp_h[i - 1][j] + dp_h[i][j - 1] - dp_h[i - 1][j - 1]
		dp_v[i][j] = dp_v[i - 1][j] + dp_v[i][j - 1] - dp_v[i - 1][j - 1]
		if a[i - 1][j] + a[i][j] == '..':
			dp_v[i][j] += 1
		if a[i][j - 1] + a[i][j] == '..':
			dp_h[i][j] += 1
q = ii()
for _ in range(q):
	(r1, c1, r2, c2) = mi()
	ans = 0
	ans += dp_h[r2][c2] - dp_h[r2][c1] - dp_h[r1 - 1][c2] + dp_h[r1 - 1][c1]
	ans += dp_v[r2][c2] - dp_v[r2][c1 - 1] - dp_v[r1][c2] + dp_v[r1][c1 - 1]
	print(ans)


(h, w) = map(int, input().split())
hor = [[0 for i in range(501)] for j in range(501)]
ver = [[0 for i in range(501)] for j in range(501)]
s = [' ' * (w + 1)]
for _ in range(h):
	s.append([' '] + list(input()))
for y in range(1, h + 1):
	for x in range(1, w + 1):
		hor[y][x] = hor[y - 1][x] + hor[y][x - 1] - hor[y - 1][x - 1] + (s[y][x] == '.' and s[y][x - 1] == '.')
		ver[y][x] = ver[y - 1][x] + ver[y][x - 1] - ver[y - 1][x - 1] + (s[y][x] == '.' and s[y - 1][x] == '.')
q = int(input())
for _ in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = hor[r2][c2] - hor[r2][c1] - hor[r1 - 1][c2] + hor[r1 - 1][c1]
	ans += ver[r2][c2] - ver[r2][c1 - 1] - ver[r1][c2] + ver[r1][c1 - 1]
	print(ans)


from collections import *
from itertools import *
from random import *
from bisect import *
from string import *
from queue import *
from heapq import *
from math import *
from re import *
from sys import *

def fast():
	return stdin.readline().strip()

def zzz():
	return [int(i) for i in fast().split()]
(z, zz) = (input, lambda : list(map(int, z().split())))
(szz, graph, mod, szzz) = (lambda : sorted(zz()), {}, 10 ** 9 + 7, lambda : sorted(zzz()))

def lcd(xnum1, xnum2):
	return xnum1 * xnum2 // gcd(xnum1, xnum2)

def output(answer):
	stdout.write(str(answer))
dx = [-1, 1, 0, 0, 1, -1, 1, -1]
dy = [0, 0, 1, -1, 1, -1, -1, 1]
(h, w) = zzz()
horizontal = [[0 for _ in range(w)] for _ in range(h)]
vertical = [[0 for _ in range(w)] for _ in range(h)]
grids = [list(fast()) for _ in range(h)]
for i in range(h):
	for j in range(1, w):
		horizontal[i][j] = horizontal[i][j - 1] + (grids[i][j] == '.' and grids[i][j - 1] == '.') * 1
for i in range(1, h):
	for j in range(w):
		vertical[i][j] = vertical[i - 1][j] + (grids[i][j] == '.' and grids[i - 1][j] == '.') * 1
for i in range(int(z())):
	(a, b, c, d) = zzz()
	ans = 0
	for x in range(a - 1, c):
		ans += horizontal[x][d - 1] - horizontal[x][b - 1]
	for x in range(b - 1, d):
		ans += vertical[c - 1][x] - vertical[a - 1][x]
	print(ans)


(n, m) = map(int, input().split())
a = [' ' + input() for i in range(n)]
a = [' ' * (m + 1)] + a
q = int(input())
col = [[0 for i in range(m + 1)] for i in range(n + 1)]
row = [[0 for i in range(m + 1)] for i in range(n + 1)]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		col[i][j] = col[i - 1][j] + col[i][j - 1] - col[i - 1][j - 1] + (a[i][j] == '.' and a[i - 1][j] == '.')
		row[i][j] = row[i - 1][j] + row[i][j - 1] - row[i - 1][j - 1] + (a[i][j] == '.' and a[i][j - 1] == '.')
for i in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	print(col[r2][c2] - col[r1][c2] - col[r2][c1 - 1] + col[r1][c1 - 1] + row[r2][c2] - row[r2][c1] - row[r1 - 1][c2] + row[r1 - 1][c1])


(h, w) = map(int, input().strip().split())
graph = [input() for i in range(h)]
dp_w = [[0 for i in range(w + 1)] for i in range(h + 1)]
dp_h = [[0 for i in range(w + 1)] for i in range(h + 1)]
for i in range(h):
	for j in range(1, w):
		if graph[i][j] == '.' and graph[i][j - 1] == '.':
			dp_w[i + 1][j + 1] = dp_w[i + 1][j] + 1
		else:
			dp_w[i + 1][j + 1] = dp_w[i + 1][j]
for i in range(1, h):
	for j in range(w):
		if graph[i][j] == '.' and graph[i - 1][j] == '.':
			dp_h[i + 1][j + 1] = dp_h[i][j + 1] + 1
		else:
			dp_h[i + 1][j + 1] = dp_h[i][j + 1]
for q in range(int(input())):
	(h1, w1, h2, w2) = map(int, input().strip().split())
	ans = 0
	for w in range(w1, w2 + 1):
		ans += dp_h[h2][w] - dp_h[h1][w]
	for h in range(h1, h2 + 1):
		ans += dp_w[h][w2] - dp_w[h][w1]
	print(ans)


import sys
import math
import heapq
from collections import defaultdict, deque
from decimal import *

def read():
	return int(input())

def readm():
	return map(int, input().split())

def readl():
	return list(map(int, input().split()))
(H, W) = readm()
rect = [input() for i in range(H)]
Q = read()
N = []
for q in range(Q):
	N.append(readl())
rowsums = [[0] * W for _ in range(H)]
colsums = [[0] * W for _ in range(H)]
for i in range(H):
	for j in range(W):
		if i == 0:
			continue
		colsums[i][j] += colsums[i - 1][j] + (1 if rect[i][j] == '.' and rect[i - 1][j] == '.' else 0)
for j in range(W):
	for i in range(H):
		if j == 0:
			continue
		rowsums[i][j] += rowsums[i][j - 1] + (1 if rect[i][j] == '.' and rect[i][j - 1] == '.' else 0)
for q in N:
	(x1, y1, x2, y2) = (q[0] - 1, q[1] - 1, q[2] - 1, q[3] - 1)
	ans = 0
	for i in range(x1, x2 + 1):
		if y1 == 0:
			ans += rowsums[i][y2]
			continue
		ans += rowsums[i][y2] - rowsums[i][y1 - 1] - (1 if rect[i][y1] == '.' and rect[i][y1 - 1] == '.' else 0)
	for j in range(y1, y2 + 1):
		if x1 == 0:
			ans += colsums[x2][j]
			continue
		ans += colsums[x2][j] - colsums[x1 - 1][j] - (1 if rect[x1][j] == '.' and rect[x1 - 1][j] == '.' else 0)
	print(ans)


def pre(matrix, n, m):
	dp1 = [[0 for i in range(m)] for j in range(n)]
	for i in range(n):
		for j in range(m):
			if j > 0:
				if matrix[i][j] == '.' and matrix[i][j - 1] == '.':
					dp1[i][j] += 1
				dp1[i][j] += dp1[i][j - 1]
	dp2 = [[0 for i in range(m)] for j in range(n)]
	for i in range(1, n):
		for j in range(m):
			if matrix[i][j] == '.' and matrix[i - 1][j] == '.':
				dp2[i][j] += 1
			dp2[i][j] += dp2[i - 1][j]
	return (dp1, dp2)

def solve(matrix, dp1, dp2, r1, c1, r2, c2, ans):
	total = 0
	for i in range(r1 - 1, r2):
		total += dp1[i][c2 - 1]
		if c1 - 2 >= 0:
			total -= dp1[i][c1 - 2]
			if matrix[i][c1 - 1] == '.' and matrix[i][c1 - 2] == '.':
				total -= 1
	for j in range(c1 - 1, c2):
		total += dp2[r2 - 1][j]
		if r1 - 2 >= 0:
			total -= dp2[r1 - 2][j]
			if matrix[r1 - 1][j] == '.' and matrix[r1 - 2][j] == '.':
				total -= 1
	ans.append(total)

def main():
	(h, w) = map(int, input().split())
	matrix = []
	for i in range(h):
		matrix.append(input())
	(dp1, dp2) = pre(matrix, h, w)
	q = int(input())
	ans = []
	for i in range(q):
		(r1, c1, r2, c2) = map(int, input().split())
		solve(matrix, dp1, dp2, r1, c1, r2, c2, ans)
	for i in ans:
		print(i)
main()


import os
import sys
import math
from io import BytesIO, IOBase
from fractions import Fraction
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
(h, w) = map(int, input().split())
a = [['' for i in range(w)] for j in range(h)]
b = [[0 for i in range(w + 1)] for j in range(h + 1)]
c = [[0 for i in range(w + 1)] for j in range(h + 1)]
for i in range(h):
	s = input()
	for j in range(w):
		a[i][j] = s[j]
for i in range(h):
	curr = 0
	mx = 0
	for j in range(w):
		if a[i][j] == '.':
			curr += 1
			b[i + 1][j + 1] = mx + max(0, curr - 1)
		else:
			mx += max(0, curr - 1)
			curr = 0
			b[i + 1][j + 1] = mx
for i in range(w):
	curr = 0
	mx = 0
	for j in range(h):
		if a[j][i] == '.':
			curr += 1
			c[j + 1][i + 1] = mx + max(0, curr - 1)
		else:
			mx += max(0, curr - 1)
			curr = 0
			c[j + 1][i + 1] = mx
for q in range(int(input())):
	(r1, c1, r2, c2) = map(int, input().split())
	res = 0
	for i in range(r1, r2 + 1):
		res += b[i][c2] - b[i][c1]
	for i in range(c1, c2 + 1):
		res += c[r2][i] - c[r1][i]
	print(res)


import os
import sys
from io import BytesIO, IOBase
mod = 10 ** 9 + 7

def main():
	(r, c) = map(int, input().split())
	arr = []
	for _ in range(r):
		arr.append(list(input()))
	dpr = [[0 for _ in range(c + 1)] for _ in range(r + 1)]
	dpc = [[0 for _ in range(c + 1)] for _ in range(r + 1)]
	for i in range(2, c + 1):
		dpr[1][i] = dpr[1][i - 1]
		if arr[0][i - 1] == '.':
			if arr[0][i - 2] == '.':
				dpr[1][i] += 1
	for i in range(2, r + 1):
		dpc[i][1] = dpc[i - 1][1]
		if arr[i - 1][0] == '.':
			if arr[i - 2][0] == '.':
				dpc[i][1] += 1
	for i in range(2, r + 1):
		for j in range(2, c + 1):
			dpr[i][j] = dpr[i - 1][j] + dpr[i][j - 1] - dpr[i - 1][j - 1]
			dpc[i][j] = dpc[i - 1][j] + dpc[i][j - 1] - dpc[i - 1][j - 1]
			if arr[i - 1][j - 1] == '.':
				if arr[i - 2][j - 1] == '.':
					dpc[i][j] += 1
				if arr[i - 1][j - 2] == '.':
					dpr[i][j] += 1
	for _ in range(int(input())):
		(r1, c1, r2, c2) = map(int, input().split())
		print(dpc[r2][c2] - dpc[r2][c1 - 1] - dpc[r1][c2] + dpc[r1][c1 - 1] + dpr[r2][c2] - dpr[r2][c1] - dpr[r1 - 1][c2] + dpr[r1 - 1][c1])
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = os.read(self._fd, max(os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
main()


from sys import maxsize, stdout, stdin, stderr
mod = int(1000000000.0 + 7)
import sys

def I():
	return int(stdin.readline())

def lint():
	return [int(x) for x in stdin.readline().split()]

def S():
	return list(map(str, input().strip()))

def grid(r, c):
	return [lint() for i in range(r)]
from collections import defaultdict, Counter, deque
import math
import heapq
from heapq import heappop, heappush
import bisect
from itertools import groupby
from itertools import permutations as comb

def gcd(a, b):
	while b:
		a %= b
		tmp = a
		a = b
		b = tmp
	return a

def lcm(a, b):
	return a // gcd(a, b) * b

def check_prime(n):
	for i in range(2, int(n ** (1 / 2)) + 1):
		if not n % i:
			return False
	return True

def nCr(n, r):
	return fact(n) // (fact(r) * fact(n - r))

def fact(n):
	res = 1
	for i in range(2, n + 1):
		res = res * i
	return res

def primefactors(n):
	num = 0
	while n % 2 == 0:
		num += 1
		n = n / 2
	for i in range(3, int(math.sqrt(n)) + 1, 2):
		while n % i == 0:
			num += 1
			n = n // i
	if n > 2:
		num += 1
	return num

def ask(a):
	print('? {}'.format(a), flush=True)
	n = I()
	return n

def dfs(i, p):
	(a, tmp) = (0, 0)
	for j in d[i]:
		if j != p:
			a += 1
			tmp += dfs(j, i)
	if a == 0:
		return 0
	return tmp / a + 1

def primeFactors(n):
	l = []
	while n % 2 == 0:
		l.append(2)
		n = n // 2
	if n > 2:
		l.append(n)
	return l
t = 1
for _ in range(t):
	(h, w) = lint()
	s = [S() for _ in range(h)]
	dp1 = [[0] * (w + 1) for _ in range(h + 1)]
	dp2 = [[0] * (w + 1) for _ in range(h + 1)]
	for i in range(1, h + 1):
		for j in range(1, w + 1):
			if j == 1:
				continue
			elif i == 1:
				if s[i - 1][j - 1] == '#':
					dp1[i][j] = dp1[i][j - 1]
				elif s[i - 1][j - 2] == '.':
					dp1[i][j] = dp1[i][j - 1] + 1
				else:
					dp1[i][j] = dp1[i][j - 1]
			elif s[i - 1][j - 1] == '#':
				dp1[i][j] = dp1[i - 1][j] + dp1[i][j - 1] - dp1[i - 1][j - 1]
			else:
				tmp = 0
				if s[i - 1][j - 2] == '.':
					tmp += 1
				dp1[i][j] = dp1[i - 1][j] + dp1[i][j - 1] - dp1[i - 1][j - 1] + tmp
	for i in range(1, h + 1):
		for j in range(1, w + 1):
			if i == 1:
				continue
			elif j == 1:
				if s[i - 1][j - 1] == '#':
					dp2[i][j] = dp2[i - 1][j]
				elif s[i - 2][j - 1] == '.':
					dp2[i][j] = dp2[i - 1][j] + 1
				else:
					dp2[i][j] = dp2[i - 1][j]
			elif s[i - 1][j - 1] == '#':
				dp2[i][j] = dp2[i - 1][j] + dp2[i][j - 1] - dp2[i - 1][j - 1]
			else:
				tmp = 0
				if s[i - 2][j - 1] == '.':
					tmp += 1
				dp2[i][j] = dp2[i - 1][j] + dp2[i][j - 1] - dp2[i - 1][j - 1] + tmp
	q = I()
	for i in range(q):
		(a, b, c, d) = lint()
		ans = 0
		ans += dp1[c][d] - (dp1[c][b] + dp1[a - 1][d] - dp1[a - 1][b])
		ans += dp2[c][d] - (dp2[a][d] + dp2[c][b - 1] - dp2[a][b - 1])
		print(ans)


import itertools, functools, math

def II(r1, c1, r2, c2, table):
	if r1 > r2:
		return 0
	if c1 > c2:
		return 0
	res = table[r2][c2]
	if r1:
		res -= table[r1 - 1][c2]
	if c1:
		res -= table[r2][c1 - 1]
	if r1 and c1:
		res += table[r1 - 1][c1 - 1]
	return res

def solve():
	(h, w) = list(map(int, input().split()))
	grid = [input() for _ in range(h)]
	row = [[0] * w for _ in range(h)]
	col = [[0] * w for _ in range(h)]
	for i in range(h):
		col_prev = 0
		row_prev = 0
		for j in range(w):
			row[i][j] = row_prev
			col[i][j] = col_prev
			if i:
				row[i][j] += row[i - 1][j]
				col[i][j] += col[i - 1][j]
			if grid[i][j] == '#':
				continue
			if i + 1 < h and grid[i + 1][j] != '#':
				row[i][j] += 1
				row_prev += 1
			if j + 1 < w and grid[i][j + 1] != '#':
				col[i][j] += 1
				col_prev += 1
	q = int(input())
	for _ in range(q):
		(r1, c1, r2, c2) = list(map(int, input().split()))
		r1 -= 1
		c1 -= 1
		r2 -= 1
		c2 -= 1
		print(II(r1, c1, r2 - 1, c2, row) + II(r1, c1, r2, c2 - 1, col))

def __starting_point():
	solve()
__starting_point()


import sys
import math
import collections
from pprint import pprint
mod = 1000000007

def vector(size, val=0):
	vec = [val for i in range(size)]
	return vec

def matrix(rowNum, colNum, val=0):
	mat = []
	for i in range(rowNum):
		collumn = [val for j in range(colNum)]
		mat.append(collumn)
	return mat
(h, w) = map(int, input().split())
g = []
for i in range(h):
	gr = input()
	g.append(gr)

def valid(i, j):
	return i >= 0 and j >= 0 and (i < h) and (j < w) and (g[i][j] != '#')
q = int(input())
ada = matrix(h + 1, w + 1)
ubha = matrix(h + 1, w + 1)
for i in range(h):
	for j in range(w):
		ada[i + 1][j + 1] = ada[i][j + 1] + ada[i + 1][j] - ada[i][j]
		ubha[i + 1][j + 1] = ubha[i][j + 1] + ubha[i + 1][j] - ubha[i][j]
		if valid(i, j):
			if valid(i - 1, j):
				ubha[i + 1][j + 1] += 1
			if valid(i, j - 1):
				ada[i + 1][j + 1] += 1
for i in range(q):
	(a, b, c, d) = map(int, input().split())
	ans = ubha[c][d] + ubha[a][b - 1] - ubha[c][b - 1] - ubha[a][d] + ada[c][d] - ada[c][b] - ada[a - 1][d] + ada[a - 1][b]
	print(ans)


import sys, io, os
try:
	Z = io.BytesIO(os.read(0, os.fstat(0).st_size)).readline
except:
	Z = lambda : sys.stdin.readline().encode()
Y = lambda : map(int, Z().split())
(H, W) = Y()
a = []
o = []
for _ in range(H):
	a.append(Z().strip())
C = [[0] * (W + 1) for i in range(H + 1)]
R = [[0] * (W + 1) for i in range(H + 1)]
for x in range(W):
	t = 0
	p = a[0][x] == 46
	for y in range(1, H):
		v = a[y][x] == 46
		if p and v:
			t += 1
		p = v
		C[y + 1][x + 1] = t + C[y + 1][x]
for y in range(H):
	t = 0
	p = a[y][0] == 46
	for x in range(1, W):
		v = a[y][x] == 46
		if p and v:
			t += 1
		p = v
		R[y + 1][x + 1] = t + R[y][x + 1]
for _ in range(int(Z())):
	(r1, c1, r2, c2) = Y()
	v = C[r2][c2] - C[r2][c1 - 1] - C[r1][c2] + C[r1][c1 - 1]
	v += R[r2][c2] - R[r2][c1] - R[r1 - 1][c2] + R[r1 - 1][c1]
	o.append(str(v))
print('\n'.join(o))


import sys
input = sys.stdin.readline

def ceil(x):
	if x != int(x):
		x = int(x) + 1
	return x

def factorial(x, m):
	val = 1
	while x > 0:
		val = val * x % m
		x -= 1
	return val

def fact(x):
	val = 1
	while x > 0:
		val *= x
		x -= 1
	return val

def swaparr(arr, a, b):
	temp = arr[a]
	arr[a] = arr[b]
	arr[b] = temp

def gcd(a, b):
	if b == 0:
		return a
	return gcd(b, a % b)

def lcm(a, b):
	return a * b // gcd(a, b)

def nCr(n, k):
	if k > n:
		return 0
	if k > n - k:
		k = n - k
	res = 1
	for i in range(k):
		res = res * (n - i)
		res = res / (i + 1)
	return int(res)

def upper_bound(a, x, lo=0, hi=None):
	if hi == None:
		hi = len(a)
	while lo < hi:
		mid = (lo + hi) // 2
		if a[mid] < x:
			lo = mid + 1
		else:
			hi = mid
	return lo

def primefs(n):
	primes = {}
	while n % 2 == 0 and n > 0:
		primes[2] = primes.get(2, 0) + 1
		n = n // 2
	for i in range(3, int(n ** 0.5) + 2, 2):
		while n % i == 0 and n > 0:
			primes[i] = primes.get(i, 0) + 1
			n = n // i
	if n > 2:
		primes[n] = primes.get(n, 0) + 1
	return primes

def power(x, y, p):
	res = 1
	x = x % p
	if x == 0:
		return 0
	while y > 0:
		if y & 1 == 1:
			res = res * x % p
		y = y >> 1
		x = x * x % p
	return res

def swap(a, b):
	temp = a
	a = b
	b = temp
	return (a, b)

def find(x, link):
	p = x
	while p != link[p]:
		p = link[p]
	while x != p:
		nex = link[x]
		link[x] = p
		x = nex
	return p

def union(x, y, link, size):
	x = find(x, link)
	y = find(y, link)
	if size[x] < size[y]:
		(x, y) = swap(x, y)
	if x != y:
		size[x] += size[y]
		link[y] = x

def sieve(n):
	prime = [True for i in range(n + 1)]
	(prime[0], prime[1]) = (False, False)
	p = 2
	while p * p <= n:
		if prime[p] == True:
			for i in range(p * p, n + 1, p):
				prime[i] = False
		p += 1
	return prime

def phi(n):
	result = n
	p = 2
	while p * p <= n:
		if n % p == 0:
			while n % p == 0:
				n = n // p
			result = result * (1.0 - 1.0 / float(p))
		p = p + 1
	if n > 1:
		result = result * (1.0 - 1.0 / float(n))
	return int(result)

def is_prime(n):
	if n == 0:
		return False
	if n == 1:
		return True
	for i in range(2, int(n ** (1 / 2)) + 1):
		if not n % i:
			return False
	return True
MAXN = int(100000.0 + 5)

def spf_sieve():
	spf[1] = 1
	for i in range(2, MAXN):
		spf[i] = i
	for i in range(4, MAXN, 2):
		spf[i] = 2
	for i in range(3, ceil(MAXN ** 0.5), 2):
		if spf[i] == i:
			for j in range(i * i, MAXN, i):
				if spf[j] == j:
					spf[j] = i
spf = [0 for i in range(MAXN)]

def factoriazation(x):
	res = []
	for i in range(2, int(x ** 0.5) + 1):
		while x % i == 0:
			res.append(i)
			x //= i
	if x != 1:
		res.append(x)
	return res

def factors(n):
	res = []
	for i in range(1, int(n ** 0.5) + 1):
		if n % i == 0:
			res.append(i)
			res.append(n // i)
	return list(set(res))

def int_array():
	return list(map(int, input().strip().split()))

def float_array():
	return list(map(float, input().strip().split()))

def str_array():
	return input().strip().split()
MOD = int(1000000000.0) + 7
CMOD = 998244353
INF = float('inf')
NINF = -float('inf')
from itertools import permutations
import math
from bisect import bisect_left

def solve():
	(h, w) = map(int, input().split())
	piles = [list(input().rstrip()) for x in range(h)]
	dot = '.'
	hatch = '#'
	dp = [[0 for i in range(w + 1)] for j in range(h + 1)]
	vr = [[0 for i in range(w + 1)] for j in range(h + 1)]
	hr = [[0 for i in range(w + 1)] for j in range(h + 1)]
	for i in range(1, w):
		if piles[0][i] == dot and piles[0][i - 1] == dot:
			dp[1][i + 1] = dp[1][i] + 1
		else:
			dp[1][i + 1] = dp[1][i]
	for i in range(1, h):
		if piles[i][0] == dot and piles[i - 1][0] == dot:
			dp[i + 1][1] = dp[i][1] + 1
		else:
			dp[i + 1][1] = dp[i][1]
	for i in range(1, h):
		for j in range(1, w):
			if piles[i][j - 1] == dot and piles[i - 1][j] == dot and (piles[i][j] == dot):
				dp[i + 1][j + 1] = dp[i + 1][j] + dp[i][j + 1] - dp[i][j] + 2
			elif piles[i][j] == hatch:
				dp[i + 1][j + 1] = dp[i + 1][j] + dp[i][j + 1] - dp[i][j]
			elif piles[i][j - 1] == dot or piles[i - 1][j] == dot:
				dp[i + 1][j + 1] = dp[i + 1][j] + dp[i][j + 1] - dp[i][j] + 1
			elif piles[i][j - 1] == hatch and piles[i - 1][j] == hatch:
				dp[i + 1][j + 1] = dp[i + 1][j] + dp[i][j + 1] - dp[i][j]
	for i in range(h):
		for j in range(w):
			if i > 0:
				if piles[i][j] == dot and piles[i - 1][j] == dot:
					vr[i + 1][j + 1] = vr[i + 1][j] + 1
				else:
					vr[i + 1][j + 1] = vr[i + 1][j]
			if j > 0:
				if piles[i][j] == dot and piles[i][j - 1] == dot:
					hr[i + 1][j + 1] = hr[i][j + 1] + 1
				else:
					hr[i + 1][j + 1] = hr[i][j + 1]
	q = int(input())
	for _ in range(q):
		(r1, c1, r2, c2) = map(int, input().split())
		val = vr[r1][c2] - vr[r1][c1 - 1] + hr[r2][c1] - hr[r1 - 1][c1]
		print(dp[r2][c2] - dp[r2][c1 - 1] - dp[r1 - 1][c2] + dp[r1 - 1][c1 - 1] - val)
for _ in range(1):
	solve()


(h, w) = map(int, input().split())
a = [input() for _ in range(h)]
dp = [[0] * (w + 1) for _ in range(h + 1)]
dp1 = [[0] * (w + 1) for _ in range(h + 1)]
for i in range(1, h + 1):
	for j in range(2, w + 1):
		dp[i][j] = dp[i][j - 1] + [0, 1][a[i - 1][j - 1] == a[i - 1][j - 2] == '.']
for i in range(1, w + 1):
	for j in range(2, h + 1):
		dp1[j][i] = dp1[j - 1][i] + [0, 1][a[j - 1][i - 1] == a[j - 2][i - 1] == '.']
for i in range(1, w + 1):
	for j in range(1, h + 1):
		dp[j][i] += dp[j - 1][i]
for i in range(1, h + 1):
	for j in range(1, w + 1):
		dp1[i][j] += dp1[i][j - 1]
for _ in range(int(input())):
	(r1, c1, r2, c2) = map(int, input().split())
	print(dp[r2][c2] - dp[r1 - 1][c2] - dp[r2][c1] + dp[r1 - 1][c1] + dp1[r2][c2] - dp1[r1][c2] - dp1[r2][c1 - 1] + dp1[r1][c1 - 1])


(n, m) = map(int, input().split())
(r, c) = ([[0 for i in range(m + 1)] for j in range(n + 1)], [[0 for i in range(m + 1)] for j in range(n + 1)])
g = [' ' * (m + 1)] + [' ' + input() for _ in range(n)]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		r[i][j] = r[i][j - 1] + r[i - 1][j] - r[i - 1][j - 1] + (g[i][j] == g[i][j - 1] == '.')
		c[i][j] = c[i][j - 1] + c[i - 1][j] - c[i - 1][j - 1] + (g[i][j] == g[i - 1][j] == '.')
q = int(input())
for _ in ' ' * q:
	(r1, c1, r2, c2) = map(int, input().split())
	print(r[r2][c2] - r[r1 - 1][c2] - r[r2][c1] + r[r1 - 1][c1] + c[r2][c2] - c[r1][c2] - c[r2][c1 - 1] + c[r1][c1 - 1])


(h, w) = map(int, input().split())
g = [list(input()) for i in range(h)]
q = int(input())
ud = [[0] * w for i in range(h - 1)]
lr = [[0] * (w - 1) for i in range(h)]
for i in range(h - 1):
	for j in range(w):
		if g[i][j] == g[i + 1][j] == '.':
			ud[i][j] += 1
for j in range(w - 1):
	for i in range(h - 1):
		ud[i][j + 1] += ud[i][j]
for j in range(w - 1):
	for i in range(h):
		if g[i][j] == g[i][j + 1] == '.':
			lr[i][j] += 1
for i in range(h - 1):
	for j in range(w - 1):
		lr[i + 1][j] += lr[i][j]
x = [[0] * (w - 1) for i in range(h)]
y = [[0] * w for i in range(h - 1)]
for i in range(h - 1):
	for j in range(w):
		if g[i][j] == g[i + 1][j] == '.':
			y[i][j] = 1
for i in range(h):
	for j in range(w - 1):
		if g[i][j] == g[i][j + 1] == '.':
			x[i][j] = 1
for i in range(h - 2):
	for j in range(w):
		y[i + 1][j] += y[i][j]
for i in range(h - 1):
	for j in range(w - 1):
		y[i][j + 1] += y[i][j]
for i in range(h):
	for j in range(w - 2):
		x[i][j + 1] += x[i][j]
for i in range(h - 1):
	for j in range(w - 1):
		x[i + 1][j] += x[i][j]
cnt = [[0] * (w + 1) for i in range(h + 1)]
for i in range(h):
	for j in range(w):
		if i == 0 and j == 0:
			continue
		elif i == 0:
			cnt[i + 1][j + 1] = x[i][j - 1]
		elif j == 0:
			cnt[i + 1][j + 1] = y[i - 1][j]
		else:
			cnt[i + 1][j + 1] = x[i][j - 1] + y[i - 1][j]
for _ in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = cnt[r2][c2] - cnt[r2][c1 - 1] - cnt[r1 - 1][c2] + cnt[r1 - 1][c1 - 1]
	if r1 >= 2:
		ans -= ud[r1 - 2][c2 - 1]
		if c1 >= 2:
			ans += ud[r1 - 2][c1 - 2]
	if c1 >= 2:
		ans -= lr[r2 - 1][c1 - 2]
		if r1 >= 2:
			ans += lr[r1 - 2][c1 - 2]
	print(ans)


(n, m) = map(int, input().split())
board = [['#'] * (m + 2)] + [['#'] + list(input()) + ['#'] for i in range(n)] + [['#'] * (m + 2)]
ansr = [[0] * (m + 2) for i in range(n + 2)]
ansc = [[0] * (m + 2) for i in range(n + 2)]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		ansr[i][j] = ansr[i - 1][j] + ansr[i][j - 1] - ansr[i - 1][j - 1] + (1 if board[i][j] == '.' and board[i][j - 1] == '.' else 0)
		ansc[i][j] = ansc[i - 1][j] + ansc[i][j - 1] - ansc[i - 1][j - 1] + (1 if board[i][j] == '.' and board[i - 1][j] == '.' else 0)
q = int(input())
for i in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	print(ansr[r2][c2] + ansc[r2][c2] - ansc[r1][c2] - ansc[r2][c1 - 1] - ansr[r1 - 1][c2] - ansr[r2][c1] + ansr[r1 - 1][c1] + ansc[r1][c1 - 1])


from __future__ import nested_scopes, generators, division, absolute_import, with_statement, print_function, unicode_literals
import sys, os, time

def rv():
	return map(int, input().split())

def rl(n):
	return [list(map(int, input().split())) for _ in range(n)]
if os.path.exists('test.txt'):
	sys.stdin = open('test.txt')

def solve():
	(rows, cols) = rv()
	tab = [input() for _ in range(rows)]
	(horizontalcount, verticalcount) = ([[0] * (cols + 1) for _ in range(rows)], [[0] * cols for _ in range(rows + 1)])
	for row in range(rows):
		for col in range(1, cols + 1):
			horizontalcount[row][col] = horizontalcount[row][col - 1] + (1 if col < cols and tab[row][col] == '.' and (tab[row][col - 1] == '.') else 0)
	for col in range(cols):
		for row in range(1, rows + 1):
			verticalcount[row][col] = verticalcount[row - 1][col] + (1 if row < rows and tab[row][col] == '.' and (tab[row - 1][col] == '.') else 0)
	(queries,) = rv()
	res = [None] * queries
	for query in range(queries):
		(r1, c1, r2, c2) = [val - 1 for val in map(int, input().split())]
		temp = 0
		for row in range(r1, r2 + 1):
			temp += horizontalcount[row][c2 + 1 - 1] - horizontalcount[row][c1]
		for col in range(c1, c2 + 1):
			temp += verticalcount[r2 + 1 - 1][col] - verticalcount[r1][col]
		res[query] = temp
	print('\n'.join(map(str, res)))
solve()


def main():
	(h, w) = map(int, input().split())
	l = [[c == '.' for c in input()] for _ in range(h)]
	ver = [[0] * (w + 1) for _ in range(h + 1)]
	for (y, aa, bb, l0, l1) in zip(range(h - 1), ver, ver[1:], l, l[1:]):
		for x in range(w):
			bb[x + 1] = (l0[x] and l1[x]) + bb[x] + aa[x + 1] - aa[x]
	hor = [[0] * (w + 1) for _ in range(h + 1)]
	for (y, aa, bb, l0) in zip(range(h), hor, hor[1:], l):
		for x in range(w - 1):
			bb[x + 1] = (l0[x] and l0[x + 1]) + bb[x] + aa[x + 1] - aa[x]
	res = []
	for _ in range(int(input())):
		(r1, c1, r2, c2) = map(int, input().split())
		r1 -= 1
		c1 -= 1
		res.append(str(ver[r2 - 1][c2] - ver[r1][c2] - ver[r2 - 1][c1] + ver[r1][c1] + hor[r2][c2 - 1] - hor[r1][c2 - 1] - hor[r2][c1] + hor[r1][c1]))
	print('\n'.join(res))
main()


(h, w) = [int(i) for i in input().split()]
maxx = 2005
ver = [[0] * maxx for j in range(maxx)]
hor = [[0] * maxx for j in range(maxx)]
s = []
for i in range(h):
	s.append(input())
for x in range(h):
	for y in range(w):
		hor[x + 1][y + 1] = hor[x][y + 1] + hor[x + 1][y] - hor[x][y]
		ver[x + 1][y + 1] = ver[x][y + 1] + ver[x + 1][y] - ver[x][y]
		if s[x][y] != '.':
			continue
		if y != w - 1 and s[x][y + 1] == '.':
			hor[x + 1][y + 1] += 1
		if x != h - 1 and s[x + 1][y] == '.':
			ver[x + 1][y + 1] += 1
q = int(input())
ans = []
print()
for _ in range(q):
	(x, y, x1, y1) = [int(i) for i in input().split()]
	a = 0
	a += hor[x1][y1 - 1] - hor[x1][y - 1] - hor[x - 1][y1 - 1] + hor[x - 1][y - 1]
	a += ver[x1 - 1][y1] - ver[x1 - 1][y - 1] - ver[x - 1][y1] + ver[x - 1][y - 1]
	ans.append(a)
for i in ans:
	print(i)


import sys
input = sys.stdin.readline
from math import ceil, floor, factorial

def swaparr(arr, a, b):
	temp = arr[a]
	arr[a] = arr[b]
	arr[b] = temp

def gcd(a, b):
	if a == 0:
		return b
	return gcd(b % a, a)

def nCr(n, k):
	if k > n - k:
		k = n - k
	res = 1
	for i in range(k):
		res = res * (n - i)
		res = res / (i + 1)
	return int(res)

def upper_bound(a, x, lo=0):
	hi = len(a)
	while lo < hi:
		mid = (lo + hi) // 2
		if a[mid] < x:
			lo = mid + 1
		else:
			hi = mid
	return lo

def primefs(n):
	primes = {}
	while n % 2 == 0:
		primes[2] = primes.get(2, 0) + 1
		n = n // 2
	for i in range(3, int(n ** 0.5) + 2, 2):
		while n % i == 0:
			primes[i] = primes.get(i, 0) + 1
			n = n // i
	if n > 2:
		primes[n] = primes.get(n, 0) + 1
	return primes

def power(x, y, p):
	res = 1
	x = x % p
	if x == 0:
		return 0
	while y > 0:
		if y & 1 == 1:
			res = res * x % p
		y = y >> 1
		x = x * x % p
	return res

def swap(a, b):
	temp = a
	a = b
	b = temp
	return (a, b)

def find(x, link):
	p = x
	while p != link[p]:
		p = link[p]
	while x != p:
		nex = link[x]
		link[x] = p
		x = nex
	return p

def union(x, y, link, size):
	x = find(x, link)
	y = find(y, link)
	if size[x] < size[y]:
		(x, y) = swap(x, y)
	if x != y:
		size[x] += size[y]
		link[y] = x

def sieve(n):
	prime = [True for i in range(n + 1)]
	p = 2
	while p * p <= n:
		if prime[p] == True:
			for i in range(p * p, n + 1, p):
				prime[i] = False
		p += 1
	return prime
MAXN = int(1000000.0 + 5)

def spf_sieve():
	spf[1] = 1
	for i in range(2, MAXN):
		spf[i] = i
	for i in range(4, MAXN, 2):
		spf[i] = 2
	for i in range(3, ceil(MAXN ** 0.5), 2):
		if spf[i] == i:
			for j in range(i * i, MAXN, i):
				if spf[j] == j:
					spf[j] = i

def factoriazation(x):
	ret = {}
	while x != 1:
		ret[spf[x]] = ret.get(spf[x], 0) + 1
		x = x // spf[x]
	return ret

def int_array():
	return list(map(int, input().strip().split()))

def str_array():
	return input().strip().split()
MOD = int(1000000000.0) + 7
CMOD = 998244353
INF = float('inf')
NINF = -float('inf')
(h, w) = int_array()
a = []
q = []
for _ in range(h):
	a.append(list(input().strip()))
for _ in range(int(input())):
	q.append(int_array())
dph = [[0 for _ in range(w)] for __ in range(h)]
dpw = [[0 for _ in range(w)] for __ in range(h)]
for i in range(h):
	for j in range(1, w):
		if a[i][j - 1] + a[i][j] == '..':
			dph[i][j] = dph[i][j - 1] + 1
		else:
			dph[i][j] = dph[i][j - 1]
for j in range(w):
	for i in range(1, h):
		if a[i - 1][j] + a[i][j] == '..':
			dpw[i][j] = dpw[i - 1][j] + 1
		else:
			dpw[i][j] = dpw[i - 1][j]
for qq in q:
	(a, b, c, d) = qq
	ans = 0
	a -= 1
	b -= 1
	c -= 1
	d -= 1
	for i in range(a, c + 1):
		ans += dph[i][d] - dph[i][b]
	for i in range(b, d + 1):
		ans += dpw[c][i] - dpw[a][i]
	print(ans)


def f():
	dp = [[0 for t in range(w)] for t in range(h)]
	for i in range(1, h):
		dp[i][0] = dp[i - 1][0]
		if mp[i][0] != '#' and mp[i - 1][0] != '#':
			dp[i][0] += 1
	for j in range(1, w):
		dp[0][j] = dp[0][j - 1]
		if mp[0][j - 1] != '#' and mp[0][j] != '#':
			dp[0][j] += 1
	for i in range(1, h):
		for j in range(1, w):
			dp[i][j] = dp[i - 1][j] + dp[i][j - 1] - dp[i - 1][j - 1]
			if mp[i][j] != '#':
				if mp[i - 1][j] != '#' and mp[i][j - 1] != '#':
					dp[i][j] += 2
				elif mp[i - 1][j] != '#' or mp[i][j - 1] != '#':
					dp[i][j] += 1
	return dp

def f2(dp, arr, mp):
	r1 = arr[0] - 1
	c1 = arr[1] - 1
	r2 = arr[2] - 1
	c2 = arr[3] - 1
	count = dp[r2][c2]
	if c1 != 0:
		count -= dp[r2][c1 - 1]
	if r1 != 0:
		count -= dp[r1 - 1][c2]
	if c1 != 0 and r1 != 0:
		count += dp[r1 - 1][c1 - 1]
	if r1 != 0:
		for itr in range(c1, c2 + 1):
			if mp[r1][itr] == '.' and mp[r1 - 1][itr] == '.':
				count -= 1
	if c1 != 0:
		for itr in range(r1, r2 + 1):
			if mp[itr][c1] == '.' and mp[itr][c1 - 1] == '.':
				count -= 1
	return count
(h, w) = map(int, input().split())
mp = []
for i in range(h):
	mp += [input()]
test = int(input())
dp = f()
for t in range(test):
	arr = list(map(int, input().split()))
	print(f2(dp, arr, mp))


from collections import Counter, OrderedDict
from itertools import permutations as perm
from fractions import Fraction
from collections import deque
from sys import stdin
from bisect import *
from heapq import *
g = lambda : stdin.readline().strip()
gl = lambda : g().split()
gil = lambda : [int(var) for var in gl()]
gfl = lambda : [float(var) for var in gl()]
gcl = lambda : list(g())
gbs = lambda : [int(var) for var in g()]
mod = int(1000000000.0) + 7
inf = float('inf')
(n, m) = gil()
mat = []
ans = [[0 for _ in range(m + 1)] for _ in range(n + 1)]
for _ in range(n):
	mat.append(g() + '#')
mat.append('#' * (m + 1))
hor = [[0 for _ in range(m + 1)] for _ in range(n + 1)]
ver = [[0 for _ in range(m + 1)] for _ in range(n + 1)]
for r in reversed(range(n)):
	for c in reversed(range(m)):
		if mat[r][c] == mat[r][c + 1] == '.':
			hor[r][c] += 1
		if mat[r][c] == mat[r + 1][c] == '.':
			ver[r][c] += 1
		hor[r][c] += hor[r][c + 1] + hor[r + 1][c] - hor[r + 1][c + 1]
		ver[r][c] += ver[r][c + 1] + ver[r + 1][c] - ver[r + 1][c + 1]

def getHor(a, b, c, d):
	ans = hor[a][b] + hor[c + 1][d] - hor[c + 1][b] - hor[a][d]
	return ans

def getVer(a, b, c, d):
	ans = ver[a][b] + ver[c][d + 1] - ver[c][b] - ver[a][d + 1]
	return ans
for _ in range(gil()[0]):
	(a, b, c, d) = gil()
	a -= 1
	b -= 1
	c -= 1
	d -= 1
	print(getVer(a, b, c, d) + getHor(a, b, c, d))


import sys
from math import *

def minp():
	return sys.stdin.readline().strip()

def mint():
	return int(minp())

def mints():
	return map(int, minp().split())
(h, w) = mints()
m = [0] * h
for i in range(h):
	m[i] = list(minp())
a = [0] * (h + 1)
a[0] = [0] * w
for i in range(h):
	tmp = [0] * w
	for j in range(w - 1):
		tmp[j + 1] = tmp[j] + (m[i][j] == '.' and m[i][j + 1] == '.')
	for j in range(w - 1):
		tmp[j + 1] += a[i][j + 1]
	a[i + 1] = tmp
b = [0] * (w + 1)
b[0] = [0] * h
for i in range(w):
	tmp = [0] * h
	for j in range(h - 1):
		tmp[j + 1] = tmp[j] + (m[j][i] == '.' and m[j + 1][i] == '.')
	for j in range(h - 1):
		tmp[j + 1] += b[i][j + 1]
	b[i + 1] = tmp
q = mint()
for i in range(q):
	(x1, y1, x2, y2) = mints()
	r = a[x2][y2 - 1] + a[x1 - 1][y1 - 1] - a[x1 - 1][y2 - 1] - a[x2][y1 - 1]
	r += b[y2][x2 - 1] + b[y1 - 1][x1 - 1] - b[y1 - 1][x2 - 1] - b[y2][x1 - 1]
	print(r)


(h, w) = list(map(int, input().split()))
field = [[c == '.' for c in input()] + [False] for i in range(h)]
field.append([False] * (w + 1))
subVerts = [[0] * (w + 1) for i in range(h + 1)]
subHoriz = [[0] * (w + 1) for i in range(h + 1)]
for y in range(h):
	subVerts[y][0] = 0
	subHoriz[y][0] = 0
for x in range(w):
	subHoriz[0][x] = 0
	subVerts[0][x] = 0
for y in range(h):
	for x in range(w):
		subVerts[y + 1][x + 1] = subVerts[y + 1][x] + subVerts[y][x + 1] - subVerts[y][x]
		if field[y][x] and field[y - 1][x]:
			subVerts[y + 1][x + 1] += 1
		subHoriz[y + 1][x + 1] = subHoriz[y + 1][x] + subHoriz[y][x + 1] - subHoriz[y][x]
		if field[y][x] and field[y][x - 1]:
			subHoriz[y + 1][x + 1] += 1
q = int(input())
for i in range(q):
	(y1, x1, y2, x2) = [int(x) - 1 for x in input().split()]
	ansHoriz = subHoriz[y2 + 1][x2 + 1] - subHoriz[y1][x2 + 1] - subHoriz[y2 + 1][x1 + 1] + subHoriz[y1][x1 + 1]
	ansVerts = subVerts[y2 + 1][x2 + 1] - subVerts[y1 + 1][x2 + 1] - subVerts[y2 + 1][x1] + subVerts[y1 + 1][x1]
	print(ansHoriz + ansVerts)


def solve():
	(numRows, numCols) = map(int, input().split())
	grid = [['#'] * (numCols + 1)]
	grid.extend((['#'] + list(input()) for row in range(numRows)))
	(h, v) = computeSolutions(numRows, numCols, grid)
	numQueries = int(input())
	for q in range(numQueries):
		(r1, c1, r2, c2) = map(int, input().split())
		print(solution(r1, c1, r2, c2, h, v))

def computeSolutions(numRows, numCols, grid):
	h = [[0 for c in range(numCols + 1)] for r in range(numRows + 1)]
	v = [[0 for c in range(numCols + 1)] for r in range(numRows + 1)]
	for r in range(1, numRows + 1):
		for c in range(1, numCols + 1):
			h[r][c] = h[r - 1][c] + h[r][c - 1] - h[r - 1][c - 1]
			v[r][c] = v[r][c - 1] + v[r - 1][c] - v[r - 1][c - 1]
			if grid[r][c] != '.':
				continue
			if grid[r][c - 1] == '.':
				h[r][c] += 1
			if grid[r - 1][c] == '.':
				v[r][c] += 1
	return (h, v)

def solution(r1, c1, r2, c2, h, v):
	s = h[r2][c2] - h[r2][c1] - h[r1 - 1][c2] + h[r1 - 1][c1]
	s += v[r2][c2] - v[r2][c1 - 1] - v[r1][c2] + v[r1][c1 - 1]
	return s
solve()


def solve(h, w, board, queries):

	def get_horiz(h, w, board):
		horiz = [[None] * w for _ in range(h)]
		for i in range(w):
			for j in range(h):
				if i == 0:
					horiz[j][i] = 0
					continue
				current = 1 if board[j][i] == '.' and board[j][i - 1] == '.' else 0
				if j == 0:
					horiz[j][i] = horiz[j][i - 1] + current
				else:
					current = 1 if board[j][i] == '.' and board[j][i - 1] == '.' else 0
					horiz[j][i] = horiz[j][i - 1] + horiz[j - 1][i] - horiz[j - 1][i - 1] + current
		return horiz
	trans = [[None] * h for _ in range(w)]
	for i in range(w):
		for j in range(h):
			trans[i][j] = board[j][i]
	horiz = get_horiz(h, w, board)
	vert = get_horiz(w, h, trans)

	def query(r1, c1, r2, c2):
		r1 -= 1
		c1 -= 1
		r2 -= 1
		c2 -= 1
		acum = 0
		for (rr1, rr2, cc1, cc2, horizvert) in [(r1, r2, c1, c2, horiz), (c1, c2, r1, r2, vert)]:
			base = horizvert[rr2][cc2]
			if rr1 > 0:
				base -= horizvert[rr1 - 1][cc2]
				base += horizvert[rr1 - 1][cc1]
			base -= horizvert[rr2][cc1]
			acum += base
		return acum
	res = []
	for q in queries:
		res.append(query(*q))
	return res
(h, w) = tuple(map(int, input().split()))
board = []
for _ in range(h):
	board.append(input())
qnum = int(input())
queries = []
for _ in range(qnum):
	queries.append(tuple(map(int, input().split())))
res = solve(h, w, board, queries)
for r in res:
	print(r)


def string2d(arr):
	return '\n'.join((' '.join(map(str, row)) for row in arr))
(H, W) = list(map(int, input().split()))
grid = [[c == '.' for c in input()] for i in range(H)]
blah1 = [[0 for j in range(W)] for i in range(H)]
blah2 = [[0 for j in range(W)] for i in range(H)]
for i in range(H):
	for j in range(W):
		if not grid[i][j]:
			continue
		if j + 1 < W and grid[i][j + 1]:
			blah1[i][j] = 1
		if i + 1 < H and grid[i + 1][j]:
			blah2[i][j] = 1
pref1 = [[0 for j in range(W + 1)] for i in range(H + 1)]
pref2 = [[0 for j in range(W + 1)] for i in range(H + 1)]
for i in range(1, H + 1):
	for j in range(1, W + 1):
		pref1[i][j] = pref1[i - 1][j] + blah1[i - 1][j - 1]
		pref2[i][j] = pref2[i - 1][j] + blah2[i - 1][j - 1]
for i in range(1, H + 1):
	for j in range(1, W + 1):
		pref1[i][j] += pref1[i][j - 1]
		pref2[i][j] += pref2[i][j - 1]
Q = int(input())
for q in range(Q):
	(r1, c1, r2, c2) = list(map(int, input().split()))
	one = pref1[r2][c2 - 1] - pref1[r2][c1 - 1] - pref1[r1 - 1][c2 - 1] + pref1[r1 - 1][c1 - 1]
	two = pref2[r2 - 1][c2] - pref2[r2 - 1][c1 - 1] - pref2[r1 - 1][c2] + pref2[r1 - 1][c1 - 1]
	print(one + two)


def transpose(grid):
	return [[grid[y][x] for y in range(len(grid))] for x in range(len(grid[0]))]

def preprocess(grid):
	st1 = [[x >= 1 and grid[y][x - 1] == grid[y][x] == '.' for x in range(len(grid[0]))] for y in range(len(grid))]
	st2 = [[0 for x in range(len(st1[0]))] for y in range(len(st1))]
	for y in range(len(st1)):
		for x in range(len(st1[0])):
			st2[y][x] = (st2[y - 1][x] if y >= 1 else 0) + (st2[y][x - 1] if x >= 1 else 0) - (st2[y - 1][x - 1] if y >= 1 and x >= 1 else 0) + int(st1[y][x])
	return st2
import pprint
(h, w) = [int(x) for x in input().split()]
grid = [input() for y in range(h)]
(pre, pre2) = (preprocess(grid), transpose(preprocess(transpose(grid))))
q = int(input())
for qi in range(q):
	(r1, c1, r2, c2) = [int(x) for x in input().split()]
	(r1, c1, r2, c2) = (r1 - 1, c1 - 1, r2 - 1, c2 - 1)
	val = pre[r2][c2] + (pre[r1 - 1][c1] if r1 >= 1 else 0) - (pre[r2][c1] if c1 >= 0 else 0) - (pre[r1 - 1][c2] if r1 >= 1 else 0) + pre2[r2][c2] + (pre2[r1][c1 - 1] if c1 >= 1 else 0) - (pre2[r2][c1 - 1] if c1 >= 1 else 0) - (pre2[r1][c2] if r1 >= 0 else 0)
	print(val)


R = lambda : map(int, input().split())
(n, m) = R()
b = [input() for _ in range(n)]
dph = [[0 for y1 in range(m + 2)] for x1 in range(n + 2)]
dpv = [[0 for y2 in range(m + 2)] for x2 in range(n + 2)]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		dpv[i][j] += (2 <= i <= n and b[i - 1][j - 1] == b[i - 2][j - 1] == '.') + dpv[i - 1][j]
		dph[i][j] += (2 <= j <= m and b[i - 1][j - 1] == b[i - 1][j - 2] == '.') + dph[i][j - 1]
for i in range(1, n + 1):
	for j in range(1, m + 1):
		dpv[i][j] += dpv[i][j - 1]
		dph[i][j] += dph[i - 1][j]
for i in range(int(input())):
	(i1, j1, i2, j2) = R()
	hc = max(0, dph[i2][j2] - dph[i2][j1] - dph[i1 - 1][j2] + dph[i1 - 1][j1])
	vc = max(0, dpv[i2][j2] - dpv[i2][j1 - 1] - dpv[i1][j2] + dpv[i1][j1 - 1])
	print(hc + vc)


import os
import sys
from io import BytesIO, IOBase
import heapq as h
from bisect import bisect_left
from types import GeneratorType
BUFSIZE = 8192

class FastIO(IOBase):
	newlines = 0

	def __init__(self, file):
		import os
		self.os = os
		self._fd = file.fileno()
		self.buffer = BytesIO()
		self.writable = 'x' in file.mode or 'r' not in file.mode
		self.write = self.buffer.write if self.writable else None

	def read(self):
		while True:
			b = self.os.read(self._fd, max(self.os.fstat(self._fd).st_size, BUFSIZE))
			if not b:
				break
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines = 0
		return self.buffer.read()

	def readline(self):
		while self.newlines == 0:
			b = self.os.read(self._fd, max(self.os.fstat(self._fd).st_size, BUFSIZE))
			self.newlines = b.count(b'\n') + (not b)
			ptr = self.buffer.tell()
			(self.buffer.seek(0, 2), self.buffer.write(b), self.buffer.seek(ptr))
		self.newlines -= 1
		return self.buffer.readline()

	def flush(self):
		if self.writable:
			self.os.write(self._fd, self.buffer.getvalue())
			(self.buffer.truncate(0), self.buffer.seek(0))

class IOWrapper(IOBase):

	def __init__(self, file):
		self.buffer = FastIO(file)
		self.flush = self.buffer.flush
		self.writable = self.buffer.writable
		self.write = lambda s: self.buffer.write(s.encode('ascii'))
		self.read = lambda : self.buffer.read().decode('ascii')
		self.readline = lambda : self.buffer.readline().decode('ascii')
(sys.stdin, sys.stdout) = (IOWrapper(sys.stdin), IOWrapper(sys.stdout))
input = lambda : sys.stdin.readline().rstrip('\r\n')
import time
start_time = time.time()
import collections as col
import math, string
from functools import reduce

def getInts():
	return [int(s) for s in input().split()]

def getInt():
	return int(input())

def getStrs():
	return [s for s in input().split()]

def getStr():
	return input()

def listStr():
	return list(input())
MOD = 10 ** 9 + 7

def solve():
	(N, M) = getInts()
	grid = []
	for n in range(N):
		grid.append(getStr())
	rows = [[]]
	cols = [[]]
	for n in range(N):
		curr = 0
		tmp = [0]
		for m in range(M - 1):
			if grid[n][m] == '.' and grid[n][m + 1] == '.':
				curr += 1
			tmp.append(curr)
		tmp.append(curr)
		rows.append(tmp)
	for m in range(M):
		curr = 0
		tmp = [0]
		for n in range(N - 1):
			if grid[n][m] == '.' and grid[n + 1][m] == '.':
				curr += 1
			tmp.append(curr)
		tmp.append(curr)
		cols.append(tmp)
	for q in range(getInt()):
		(r1, c1, r2, c2) = getInts()
		ans = 0
		for c in range(c1, c2 + 1):
			ans += cols[c][r2 - 1] - cols[c][r1 - 1]
		for r in range(r1, r2 + 1):
			ans += rows[r][c2 - 1] - rows[r][c1 - 1]
		print(ans)
	return
solve()


(n, m) = map(int, input().split())
a = [[] for i in range(n)]
for i in range(n):
	a[i] = list(input())
(hor, ver) = ([[0] * 2005 for i in range(2005)], [[0] * 2005 for i in range(2005)])
for i in range(0, n + 1):
	for j in range(0, m + 1):
		if i == 0 or j == 0:
			ver[i][j] = hor[i][j] = 0
		else:
			ver[i][j] = ver[i - 1][j] + ver[i][j - 1] - ver[i - 1][j - 1]
			hor[i][j] = hor[i - 1][j] + hor[i][j - 1] - hor[i - 1][j - 1]
			if i < n and a[i - 1][j - 1] == '.' and (a[i][j - 1] == '.'):
				ver[i][j] += 1
			if j < m and a[i - 1][j - 1] == '.' and (a[i - 1][j] == '.'):
				hor[i][j] += 1
for _ in range(int(input())):
	(xb, yb, xa, ya) = map(int, input().split())
	ans = 0
	ans += hor[xa][ya - 1] - hor[xb - 1][ya - 1] - hor[xa][yb - 1] + hor[xb - 1][yb - 1]
	ans += ver[xa - 1][ya] - ver[xa - 1][yb - 1] - ver[xb - 1][ya] + ver[xb - 1][yb - 1]
	print(ans)


def ckrow(r, c1, c2):
	k = 0
	for i in range(c1 + 1, c2 + 1):
		if g[r][i] == g[r][i - 1] == '.':
			k += 1
	return k

def ckcol(r, c1, c2):
	k = 0
	for i in range(c1 + 1, c2 + 1):
		if g[i][r] == g[i - 1][r] == '.':
			k += 1
	return k
(h, w) = map(int, input().split())
g = ['#' * (w + 1)]
for _ in range(h):
	g.append('#' + input())
dp = [[0 for i in range(w + 1)] for i in range(h + 1)]
for i in range(1, h + 1):
	for j in range(1, w + 1):
		if g[i][j] == '#':
			dp[i][j] = dp[i - 1][j] + dp[i][j - 1] - dp[i - 1][j - 1]
		else:
			(x, y) = (dp[i - 1][j], dp[i][j - 1])
			x += 1 if g[i - 1][j] == '.' else 0
			y += 1 if g[i][j - 1] == '.' else 0
			dp[i][j] = x + y - dp[i - 1][j - 1]
for _ in range(int(input())):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = dp[r1][c1] + dp[r2][c2] - dp[r1][c2] - dp[r2][c1]
	ans += ckrow(r1, c1, c2)
	ans += ckcol(c1, r1, r2)
	print(ans)


import math as mt
import sys, string
input = sys.stdin.readline
import random
from collections import deque, defaultdict
L = lambda : list(map(int, input().split()))
Ls = lambda : list(input().split())
M = lambda : map(int, input().split())
I = lambda : int(input())
(n, m) = M()
l = []
x = []
y = []
for i in range(n):
	w = [0]
	t = list(input().strip())
	l.append(t)
	for j in range(1, m):
		if t[j] == t[j - 1] and t[j] == '.':
			w.append(1 + w[-1])
		else:
			w.append(w[-1])
	x.append(w)
for i in range(m):
	w = [0]
	for j in range(1, n):
		if l[j][i] == l[j - 1][i] and l[j][i] == '.':
			w.append(1 + w[-1])
		else:
			w.append(w[-1])
	y.append(w)
q = I()
for i in range(q):
	(a, b, c, d) = M()
	a -= 1
	b -= 1
	c -= 1
	d -= 1
	ans = 0
	for j in range(a, c + 1):
		ans += x[j][d] - x[j][b]
	for j in range(b, d + 1):
		ans += y[j][c] - y[j][a]
	print(ans)


import sys
input = sys.stdin.readline
(h, w) = map(int, input().split())
mat = []
pcol = []
for i in range(h):
	s = input()
	mat.append(s)
	o = []
	for j in range(w):
		o.append(0)
	pcol.append(o)
prow = []
for i in range(h):
	x = mat[i]
	o = [0]
	cnt = 0
	for j in range(1, w):
		if x[j - 1] == '.' and x[j] == '.':
			cnt += 1
		o.append(cnt)
	prow.append(o)
for j in range(w):
	cnt = 0
	for i in range(1, h):
		if mat[i][j] == '.' and mat[i - 1][j] == '.':
			cnt += 1
		pcol[i][j] = cnt
for _ in range(int(input())):
	(r1, c1, r2, c2) = map(int, input().split())
	r1 -= 1
	r2 -= 1
	c1 -= 1
	c2 -= 1
	ans = 0
	for i in range(r1, r2 + 1):
		ans += prow[i][c2] - prow[i][c1]
	for i in range(c1, c2 + 1):
		ans += pcol[r2][i] - pcol[r1][i]
	sys.stdout.write(str(ans) + '\n')


(h, w) = map(int, input().split())
a = []
b = []
c = []
a.append('#' * (w + 1))
for i in range(h):
	a.append('#' + input())
h += 1
w += 1
for i in range(h):
	b.append([0] * w)
	c.append([0] * w)
for i in range(1, h):
	for j in range(1, w):
		b[i][j] = b[i - 1][j] + b[i][j - 1] - b[i - 1][j - 1]
		c[i][j] = c[i - 1][j] + c[i][j - 1] - c[i - 1][j - 1]
		if a[i][j] + a[i][j - 1] == '..':
			b[i][j] += 1
		if a[i][j] + a[i - 1][j] == '..':
			c[i][j] += 1
q = int(input())
for i in range(q):
	(r1, c1, r2, c2) = map(int, input().split())
	ans = b[r2][c2] - b[r1 - 1][c2] - b[r2][c1] + b[r1 - 1][c1]
	ans += c[r2][c2] - c[r1][c2] - c[r2][c1 - 1] + c[r1][c1 - 1]
	print(ans)