charmapx を改造しているときに気づいたこと。 たとえば, 下のようなプログラムを書いたとする (エラー処理は省略した)。
#include <windows.h>
#include <stdio.h>
static void tst(HDC hdc, UINT n) {
ABC abc;
if (GetCharABCWidthsW(hdc, n, n, &abc))
printf("ABC of %06X: (%d,%d,%d)\n", n,
abc.abcA, abc.abcB, abc.abcC);
else
printf("can't get ABC of %06X\n", n);
}
int main() {
HFONT hF = CreateFont(-18, 0, 0, 0, FW_NORMAL,FALSE,FALSE,FALSE,
DEFAULT_CHARSET, OUT_TT_PRECIS,
CLIP_DEFAULT_PRECIS, DEFAULT_QUALITY,
DEFAULT_PITCH|FF_SWISS, "Tahoma");
HDC hdc = GetDC(0);
HFONT hF0 = (HFONT)SelectObject(hdc, hF);
tst(hdc, 0x3042); /* ひらがな「あ」 */
tst(hdc, 0x2000B); /* 点のある「丈」 */
SelectObject(hdc, hF0);
ReleaseDC(0, hdc);
return 0;
}
Vista で動かした結果は, 0x3042 で (0,13,2), 0x2000B で (1,8,0) となる。 どうみても 0x2000B のほうは幅がせますぎる。 どうやら GetCharABCWidthsW は文字コードの下位 16ビット以外を無視するようだ。 GetCharABCWidthsI もためしてみたが, 結果はおなじ。
とりあえず BMP 以外の文字については GetCharABCWidthsW を使わないように回避コードを書いたが, アドホックすぎる回避策なので, どうにかしたいところ。
投稿時刻 2007-06-24(己丑) 06:18 於 プログラミング | コメント (0)
いままで Perl があればじゅうぶんで, Python は, 「だれかが Python で書いたプログラムに手をくわえるとき」 くらいしか必要ないとおもっていたのだが, ちょっと興味がでてきた。
というのは, Python が LL言語であるのを知って, 「Pascal に似てる」 と感じたからだ。 そう思って類似点をかんがえていくと,
など, 共通点はかなり多い。 そういうことであれば, C と Pascal がおなじようなことしかできなくても, 両方に存在価値があるのと同様, Perl と Python はそれぞれに価値がある言語だとおもえてきた。 参考書などでは Python に影響をあたえた言語として, Lisp や関数型言語しかあげていないので, いままでこのことに気づかなかったのは, うかつだった。 今後は 「Python は, スクリプト言語界の Pascal」 と考えることにしよう。
投稿時刻 2007-01-22(丙辰) 15:51 於 プログラミング | コメント (0)
Eclipse のことを書いていておもいだしたが, アノテーションに関して, Eclipse 3.2 の JDT がコンパイルできるのに, javac (1.5.0_06) ではコンパイルできないプログラムがあることをおもいだした。
たとえば, JUnit4 の @SuiteClasses アノテーションをつかって, こんな書きかたをした場合。
package samp;
import org.junit.runner.RunWith;
import org.junit.runners.Suite;
import org.junit.runners.Suite.SuiteClasses;
@RunWith(Suite.class)
@SuiteClasses({ Sample1Test.class,
Sample2Test.class,
})
public class AllTests {
}
Eclipse JDT ではエラーなしにコンパイルできるのに, javac ではコンパイルできない。 「Sample2Test.class,」 の最後の「,」がなければコンパイルできる。
Java Language Specifications の 9章 を見るに,
ElementValueArrayInitializer:
{ ElementValuesopt ,opt }
ElementValues:
ElementValue
ElementValues , ElementValue
となっているので, さいごに「,」があっても構わないようだ。
Eclipse 上でコンパイルできたソースが javac からうまくコンパイルできないことは多いが, たいていはクラスローダーがらみ(nested jar とか)であって, こういう基本的なところでちがいがでるのはめずらしい。
投稿時刻 2006-09-05(丁酉) 13:11 於 プログラミング | コメント (0)
Apache の APR 最新版 (1.3.0) は MinGW でビルドできるようになっているのを知ったので, やってみた。
以上。 結果だけ書けば簡単そうだが, じっさいは MSYS に慣れずにひどく試行錯誤したので, 書いておく。
投稿時刻 2006-09-04(丙申) 12:02 於 プログラミング | コメント (0)
いまごろ…… といわれそうだが, なるべくスクリプト自身をかきなおさずに Perl 5.8.x で JPerl のスクリプトを動かす方法についてのメモ。 動作は Windows XP 上の Active Perl 5.8.6 で確認した。
さいしょ, 「:std」の使いかたがよくわからなかったため, use encoding と use open を両方指定すると STDOUT への出力がおかしくなってしまい, ひじょうに悩んだ。 「-Mopen=:encoding(SJIS)」 のかわりに, 「-Mopen=IN,:encoding(SJIS)」 として入力だけ変更し, STDERR はソースを書きかえて binmode で切りかえたりしていたが, 意味のない話だった。
投稿時刻 2005-05-06(庚寅) 11:01 於 プログラミング | コメント (1)
C のばあいに補足。 C99 では, 「/」はかならず 0 に向かって切りすてることにあらためられた。
なお, div や ldiv は C99 にもある。 さらに long long int 用の lldiv というのもある。
投稿時刻 2005-03-16(己亥) 10:40 於 プログラミング | コメント (0)
前回の補足。
Java の整数は 2の補数表現をとっているが, int x = Integer.MIN_VALUE; のとき, x/(-1) は x に等しい。 いっぽう, x%(-1) は 0 になる。 いずれのばあいも例外は発生しない。
また, このとき x*(-1) も x に等しくなるので, x == (x/y)*y + (x%y) はこのときも成立する。
Ada では, 制約のない型(整数でいうと, Pascal でいう部分範囲型でないもの) に対する演算の結果がその型の範囲をこえたとき, 例外を発生するかどうかは実装に依存する。 GNAT では例外を発生しないようである。
C の規格では, このようなばあいは, 0 で割ったばあいとおなじく, 未定義になる。
C# の /, % 演算子は Java のばあいとまったくおなじ動作をする。
Fortran では整数に対する除算演算子 / は 0 にむかって切りすてる。 また, 組みこみ関数 MOD(x,y) は Modula-2 の REM とおなじである。 Fortran 90 以降はもうひとつ MODULO(x,y) という組みこみ関数が追加されたが, こちらは Ada の mod 演算子と(y が負のときをふくめて)おなじうごきをする。
投稿時刻 2005-03-11(甲午) 11:07 於 プログラミング | コメント (3)
整数の割り算 x div y は, x を y で割った結果を絶対値の小さくなるように切りすてた結果である。 あまりをもとめる演算子は存在せず, x - (x div y)*y をつかう。
これとはべつに x mod y があり, こちらは 0 以上 y 未満の値をかえす。 ただし y は正の整数でなければならない。 x が 0 以上であれば, x = (x div y)*y + (x mod y) がなりたつ。
ただし, ISO 7185 規格ができる前の Jensen and Wirth 2版では 「a mod b = a - ((a div b)*b)」 と書いてあることもあって, じっさいには mod を div に対応するあまりとして実装している処理系が多い。 Delphi や Free Pascal はそうなっている。 GNU Pascal は規格どおり実装している。
div 演算子はなく, 整数除算でも「/」をつかうが, Pascal とおなじく絶対値が小さくなるように切りすてる。 あまりを求める演算子には rem があり, x rem y = x - (x/y)*y である。
いっぽう Pascal とおなじ mod 演算子もある。 Pascal とことなり, x mod y の y が負であってもよい。 x と y の符号が等しいばあい, x rem y と x mod y は同じ値で, それ以外のばあいは, (x rem y) + (x mod y) = x である。
ひとつの言語に rem と mod の両方を用意したのはあまり評判がよくないようだ。 どっちかはパッケージで供給するようにすればじゅうぶんだったかもしれない。
Wirth は DIV, MOD 演算子についてあちこちで矛盾した記述をしているが, ISO/IEC 10514 規格では, / REM DIV MOD の 4つの演算子が用意されている。 これは Wirth 「Algorithms & Data Structures」(1986) の記述とひとしい。
「/」「REM」「MOD」は同名の Ada の演算子とおなじ。 x DIV y は Pascal のものとちがって, x を y で割った結果以下で最大の整数を返し, つねに (x DIV y)*y + (x MOD y) = x がなりたつ。 ただし, Ada とことなり, x DIV y と x MOD y はいずれも y が正の整数のときのみ定義されている。
規格では, (x / y)*y + (x % y) == x がなりたつとするだけで, Modula-2 でいう「/, REM」の意味であるか, 「DIV, MOD」の意味であるかは処理系依存とする。 Rationale をみると, これをどちらかにさだめたいという意見はあったようだが, 却下されたようだ。 そのかわり, Modula-2 の「/, REM」とおなじ結果を返すことを保証する div および ldiv が標準ライブラリに用意されている。 「DIV, MOD」とおなじ結果を返す関数は用意されていない。 (C99 での変更について補足)
じっさいにためしたところでは, Intel Windows 用の処理系(Visual C++ 6 および 7, Borland C++ Builder 6, MinGW) および Sparc Solaris 用の処理系(Sun Studio 7, gcc) はいずれも 「/, %」が Modula-2 の「/, REM」とおなじ結果をかえした。
「/」の意味は絶対値が小さくなるように切りすてると決められている。 Modula-2 の「DIV, MOD」にあたる演算子はないが, java.math.BigInteger クラスには remainder と mod のふたつのメソッドが定義されていて, それぞれ Modula-2 の REM と MOD にひとしい。 mod(x,y) は y が正の整数でないばあい, 例外を投げる。
なお, 日本語版の API ライブラリの解説の mod のところ で,
このメソッドは、常に「負でない」 BigInteger を返す remainder とは異なります。
とあるのは誤訳で, じっさいには remainder は負の値をかえすことがあるが, mod は負でない値をかえす。 英語原文 では,
This method differs from remainder in that it always returns a non-negative BigInteger.
と, 正しく記述されている。
投稿時刻 2005-03-11(甲午) 05:48 於 プログラミング | コメント (1)
CLU の文法についてちょっと疑問があったので, MIT の 公式サイト にいってみたのだが, げんざい anonymous ftp が利用できないようだ。 うーんざんねん。
投稿時刻 2005-01-13(丁酉) 17:00 於 プログラミング | コメント (0)
Page 1 of 1: 1