MCPcopy Create free account
hub / github.com/CompVis/diff2flow / CrossAttention

Class CrossAttention

diff2flow/models/unet/attention.py:143–192  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

141
142
143class CrossAttention(nn.Module):
144 def __init__(self, query_dim, context_dim=None, heads=8, dim_head=64, dropout=0.):
145 super().__init__()
146 inner_dim = dim_head * heads
147 context_dim = default(context_dim, query_dim)
148
149 self.scale = dim_head ** -0.5
150 self.heads = heads
151
152 self.to_q = nn.Linear(query_dim, inner_dim, bias=False)
153 self.to_k = nn.Linear(context_dim, inner_dim, bias=False)
154 self.to_v = nn.Linear(context_dim, inner_dim, bias=False)
155
156 self.to_out = nn.Sequential(
157 nn.Linear(inner_dim, query_dim),
158 nn.Dropout(dropout)
159 )
160
161 def forward(self, x, context=None, mask=None):
162 h = self.heads
163
164 q = self.to_q(x)
165 context = default(context, x)
166 k = self.to_k(context)
167 v = self.to_v(context)
168
169 q, k, v = map(lambda t: rearrange(t, 'b n (h d) -> (b h) n d', h=h), (q, k, v))
170
171 # force cast to fp32 to avoid overflowing
172 if _ATTN_PRECISION =="fp32":
173 with torch.autocast(enabled=False, device_type = 'cuda'):
174 q, k = q.float(), k.float()
175 sim = einsum('b i d, b j d -> b i j', q, k) * self.scale
176 else:
177 sim = einsum('b i d, b j d -> b i j', q, k) * self.scale
178
179 del q, k
180
181 if exists(mask):
182 mask = rearrange(mask, 'b ... -> b (...)')
183 max_neg_value = -torch.finfo(sim.dtype).max
184 mask = repeat(mask, 'b j -> (b h) () j', h=h)
185 sim.masked_fill_(~mask, max_neg_value)
186
187 # attention, what we cannot get enough of
188 sim = sim.softmax(dim=-1)
189
190 out = einsum('b i j, b j d -> b i d', sim, v)
191 out = rearrange(out, '(b h) n d -> b n (h d)', h=h)
192 return self.to_out(out)
193
194
195class MemoryEfficientCrossAttention(nn.Module):

Callers

nothing calls this directly

Calls

no outgoing calls

Tested by

no test coverage detected