📄 algebra_8cpp-source.html
字号:
00172 }00173 <span class="keywordflow">return</span> result;00174 }00175 00176 <span class="keyword">template</span> <<span class="keyword">class</span> Element, <span class="keyword">class</span> Iterator> Element GeneralCascadeMultiplication(<span class="keyword">const</span> <a class="code" href="class_abstract_group.html">AbstractGroup<Element></a> &group, Iterator begin, Iterator end)00177 {00178 <span class="keywordflow">if</span> (end-begin == 1)00179 <span class="keywordflow">return</span> group.<a class="code" href="class_abstract_group.html#_euclidean_domain_ofa23">ScalarMultiply</a>(begin->base, begin->exponent);00180 <span class="keywordflow">else</span> <span class="keywordflow">if</span> (end-begin == 2)00181 <span class="keywordflow">return</span> group.<a class="code" href="class_abstract_group.html#_euclidean_domain_ofa24">CascadeScalarMultiply</a>(begin->base, begin->exponent, (begin+1)->base, (begin+1)->exponent);00182 <span class="keywordflow">else</span>00183 {00184 <a class="code" href="class_integer.html">Integer</a> q, t;00185 Iterator last = end;00186 --last;00187 00188 std::make_heap(begin, end);00189 std::pop_heap(begin, end);00190 00191 <span class="keywordflow">while</span> (!!begin->exponent)00192 {00193 <span class="comment">// last->exponent is largest exponent, begin->exponent is next largest</span>00194 t = last->exponent;00195 <a class="code" href="class_integer.html#_integerz49_9">Integer::Divide</a>(last->exponent, q, t, begin->exponent);00196 00197 <span class="keywordflow">if</span> (q == <a class="code" href="class_integer.html#_integerz37_11">Integer::One</a>())00198 group.<a class="code" href="class_abstract_group.html#_abstract_ringa20">Accumulate</a>(begin->base, last->base); <span class="comment">// avoid overhead of ScalarMultiply()</span>00199 <span class="keywordflow">else</span>00200 group.<a class="code" href="class_abstract_group.html#_abstract_ringa20">Accumulate</a>(begin->base, group.<a class="code" href="class_abstract_group.html#_euclidean_domain_ofa23">ScalarMultiply</a>(last->base, q));00201 00202 std::push_heap(begin, end);00203 std::pop_heap(begin, end);00204 }00205 00206 <span class="keywordflow">return</span> group.<a class="code" href="class_abstract_group.html#_euclidean_domain_ofa23">ScalarMultiply</a>(last->base, last->exponent);00207 }00208 }00209 00210 <span class="keyword">struct </span>WindowSlider00211 {00212 WindowSlider(<span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> &exp, <span class="keywordtype">bool</span> fastNegate, <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> windowSizeIn=0)00213 : exp(exp), windowModulus(<a class="code" href="class_integer.html">Integer</a>::One()), windowSize(windowSizeIn), windowBegin(0), fastNegate(fastNegate), firstTime(true), finished(false)00214 {00215 <span class="keywordflow">if</span> (windowSize == 0)00216 {00217 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> expLen = exp.<a class="code" href="class_integer.html#_integerz41_2">BitCount</a>();00218 windowSize = expLen <= 17 ? 1 : (expLen <= 24 ? 2 : (expLen <= 70 ? 3 : (expLen <= 197 ? 4 : (expLen <= 539 ? 5 : (expLen <= 1434 ? 6 : 7)))));00219 }00220 windowModulus <<= windowSize;00221 }00222 00223 <span class="keywordtype">void</span> FindNextWindow()00224 {00225 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> expLen = exp.WordCount() * WORD_BITS;00226 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> skipCount = firstTime ? 0 : windowSize;00227 firstTime = <span class="keyword">false</span>;00228 <span class="keywordflow">while</span> (!exp.GetBit(skipCount))00229 {00230 <span class="keywordflow">if</span> (skipCount >= expLen)00231 {00232 finished = <span class="keyword">true</span>;00233 <span class="keywordflow">return</span>;00234 }00235 skipCount++;00236 }00237 00238 exp >>= skipCount;00239 windowBegin += skipCount;00240 expWindow = exp % (1 << windowSize);00241 00242 <span class="keywordflow">if</span> (fastNegate && exp.GetBit(windowSize))00243 {00244 negateNext = <span class="keyword">true</span>;00245 expWindow = (1 << windowSize) - expWindow;00246 exp += windowModulus;00247 }00248 <span class="keywordflow">else</span>00249 negateNext = <span class="keyword">false</span>;00250 }00251 00252 <a class="code" href="class_integer.html">Integer</a> exp, windowModulus;00253 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> windowSize, windowBegin, expWindow;00254 <span class="keywordtype">bool</span> fastNegate, negateNext, firstTime, finished;00255 };00256 00257 <span class="keyword">template</span> <<span class="keyword">class</span> T>00258 <span class="keywordtype">void</span> <a class="code" href="class_abstract_group.html">AbstractGroup<T>::SimultaneousMultiply</a>(T *results, <span class="keyword">const</span> T &base, <span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> *expBegin, <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> expCount)<span class="keyword"> const</span>00259 <span class="keyword"></span>{00260 std::vector<std::vector<Element> > buckets(expCount);00261 std::vector<WindowSlider> exponents;00262 exponents.reserve(expCount);00263 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> i;00264 00265 <span class="keywordflow">for</span> (i=0; i<expCount; i++)00266 {00267 assert(expBegin-><a class="code" href="class_integer.html#_integerz41_11">NotNegative</a>());00268 exponents.push_back(WindowSlider(*expBegin++, InversionIsFast(), 0));00269 exponents[i].FindNextWindow();00270 buckets[i].resize(1<<(exponents[i].windowSize-1), Identity());00271 }00272 00273 <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> expBitPosition = 0;00274 Element g = base;00275 <span class="keywordtype">bool</span> notDone = <span class="keyword">true</span>;00276 00277 <span class="keywordflow">while</span> (notDone)00278 {00279 notDone = <span class="keyword">false</span>;00280 <span class="keywordflow">for</span> (i=0; i<expCount; i++)00281 {00282 <span class="keywordflow">if</span> (!exponents[i].finished && expBitPosition == exponents[i].windowBegin)00283 {00284 Element &bucket = buckets[i][exponents[i].expWindow/2];00285 <span class="keywordflow">if</span> (exponents[i].negateNext)00286 Accumulate(bucket, Inverse(g));00287 <span class="keywordflow">else</span>00288 Accumulate(bucket, g);00289 exponents[i].FindNextWindow();00290 }00291 notDone = notDone || !exponents[i].finished;00292 }00293 00294 <span class="keywordflow">if</span> (notDone)00295 {00296 g = Double(g);00297 expBitPosition++;00298 }00299 }00300 00301 <span class="keywordflow">for</span> (i=0; i<expCount; i++)00302 {00303 Element &r = *results++;00304 r = buckets[i][buckets[i].size()-1];00305 <span class="keywordflow">if</span> (buckets[i].size() > 1)00306 {00307 <span class="keywordflow">for</span> (<span class="keywordtype">int</span> j = buckets[i].size()-2; j >= 1; j--)00308 {00309 Accumulate(buckets[i][j], buckets[i][j+1]);00310 Accumulate(r, buckets[i][j]);00311 }00312 Accumulate(buckets[i][0], buckets[i][1]);00313 r = Add(Double(r), buckets[i][0]);00314 }00315 }00316 }00317 00318 <span class="keyword">template</span> <<span class="keyword">class</span> T> T <a class="code" href="class_abstract_ring.html">AbstractRing<T>::Exponentiate</a>(<span class="keyword">const</span> Element &base, <span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> &exponent)<span class="keyword"> const</span>00319 <span class="keyword"></span>{00320 Element result;00321 SimultaneousExponentiate(&result, base, &exponent, 1);00322 <span class="keywordflow">return</span> result;00323 }00324 00325 <span class="keyword">template</span> <<span class="keyword">class</span> T> T <a class="code" href="class_abstract_ring.html">AbstractRing<T>::CascadeExponentiate</a>(<span class="keyword">const</span> Element &x, <span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> &e1, <span class="keyword">const</span> Element &y, <span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> &e2)<span class="keyword"> const</span>00326 <span class="keyword"></span>{00327 <span class="keywordflow">return</span> MultiplicativeGroup().AbstractGroup<T>::CascadeScalarMultiply(x, e1, y, e2);00328 }00329 00330 <span class="keyword">template</span> <<span class="keyword">class</span> Element, <span class="keyword">class</span> Iterator> Element GeneralCascadeExponentiation(<span class="keyword">const</span> <a class="code" href="class_abstract_ring.html">AbstractRing<Element></a> &ring, Iterator begin, Iterator end)00331 {00332 <span class="keywordflow">return</span> GeneralCascadeMultiplication<Element>(ring.<a class="code" href="class_abstract_ring.html#_euclidean_domain_ofa21">MultiplicativeGroup</a>(), begin, end);00333 }00334 00335 <span class="keyword">template</span> <<span class="keyword">class</span> T>00336 <span class="keywordtype">void</span> <a class="code" href="class_abstract_ring.html">AbstractRing<T>::SimultaneousExponentiate</a>(T *results, <span class="keyword">const</span> T &base, <span class="keyword">const</span> <a class="code" href="class_integer.html">Integer</a> *exponents, <span class="keywordtype">unsigned</span> <span class="keywordtype">int</span> expCount)<span class="keyword"> const</span>00337 <span class="keyword"></span>{00338 MultiplicativeGroup().AbstractGroup<T>::SimultaneousMultiply(results, base, exponents, expCount);00339 }00340 00341 NAMESPACE_END</pre></div><hr size="1"><address style="align: right;"><small>Generated on Tue Jul 8 23:34:07 2003 for Crypto++ by<a href="http://www.doxygen.org/index.html"><img src="doxygen.png" alt="doxygen" align="middle" border=0 > </a>1.3.2 </small></address></body></html>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -