プログラミング言語 Go は Google が 2009 年秋にオープンソースで公開した新しいプログラミング言語です。C や C++ のようなコンパイル言語の良さをもちつつ、Python のような動的言語でのプログラムの書き易さを兼ねそなえた特徴をもっています。クラスを使わないオブジェクト指向の言語で、コンカレントに実行するための仕組みもそなえています。 プログラミングをより速く、より生産的に、そしてより楽しくしてくれる新しいプログラミング言語 Go について説明します。
This slide is a trail CHT analysis for relatively complex bodies with chtMultiRegionFoam which is an solver of OpenFOAM. Two methods to make mesh are explained.
This slide is a trail CHT analysis for relatively complex bodies with chtMultiRegionFoam which is an solver of OpenFOAM. Two methods to make mesh are explained.
Event : Visual Studio Users Community Japan #1
Date : 2019/09/14
ソフトウェア/サービス開発において最も後回しにされるものの代表が「パフォーマンスの向上」です。C#/.NET の最大の武器は開発生産性ですが、C# 7.0 以降はパフォーマンス向上のための機能追加が多数行われています。いくつかのポイントを押さえることで実装時からより高速なコードを書くことができるようになります。
このドキュメントでは、そんなポイントとなる箇所をふんだんにお届けします。
4. 集合での列挙型の要素の使用
例えば、文字のスタイルを表現する時
?
従来の方法だと int enum パターンを使用
?
// ビットフィールド列挙定数 - 廃れている!
public class Text {
public static final int STYLE_BOLD
public static final int STYLE_ITALIC
public static final int STYLE_UNDERLINE
public static final int STYLE_STRIKETHROUGH
=
=
=
=
1
1
1
1
<<
<<
<<
<<
0;
1;
2;
3;
//
//
//
//
1
2
4
8
// パラメータは、0 個以上の STYLE_ 定数のビット
public void applyStyles(int styles) { ... }
}
今頃の Java では EnumSet を使用するべき
?
// EnumSet - ビットフィールドの最新の置換
public class Text {
public enum Style { BOLD, ITALIC, UNDERLINE, STRIKETHROUGH }
// どんな Set でも渡せるが、 EnumSet が明らかに最善
public void applyStyles(Set<Style> styles) { ... }
}
4
5. 従来の方法の場合
int enum パターン使用
?
?
ビット演算で集合操作を効率よく行うことができる
text.applyStyles(STYLE_BOLD | STYLE_ITALIC);
?
?
共通集合(要素存在確認): A & B
?
?
和集合(要素追加): A | B
要素削除: A & (~B)
要素数が多くなると、数値の解釈が困難
?
例えば最大 26 個の要素を持つ集合を定義すると
public static final int ELEM_A = 1 << 0;
// 1
public static final int ELEM_B = 1 << 1;
// 2
...
public static final int ELEM_Z = 1 << 25; // 2^25 = 33554432 (!)
...
private int elemSet = 0;
...
System.out.println(Integer.toBinaryString(elemSet)); // こんなの出されても分からないよ...>_<
5
6. 従来の方法の場合
int enum パターン使用(続き)
?
?
型安全ではない
// 枠線設定用定数
public static final int UPPER_BORDER
= 1 << 4; // 16
...
text.applyStyles(STYLE_BOLD | UPPER_BORDER); // 関係のない枠線定数を入れても文句を言ってくれない...
?
集合内の要素をイテレートするのは大変
// 定数に対応する情報も自前で管理しなければいけない
private static final String STYLE_NAME[] =
{ "BOLD", "ITALIC", "UNDERLINE", "STRIKETHROUGHT" };
...
// 要素をイテレートして、対応するスタイル名を出力
for (int offset = 0; offset < 4; offset++) {
if ((this.styles & 1 << offset) != 0) {
System.out.printf(“%s ”, STYLE_NAME[offset]);
}
}
?
6
要素数が int や long 型のビット数を超えるとさらに大変…
7. 新しい方法の場合
EnumSet 使用
?
?
?
型安全、可読性向上
要素数が 64 個以下なら、一つの long で表現される
class RegularEnumSet<E extends Enum<E>> extends EnumSet<E> {
/**
* Bit vector representation of this set. The 2^k bit indicates the
* presence of universe[k] in this set.
*/
private long elements = 0L;
?
?
集合操作はビット演算で実装される
要素数が 65 を超えた場合、 long の配列で表現される
class JumboEnumSet<E extends Enum<E>> extends EnumSet<E> {
/**
* Bit vector representation of this set. The ith bit of the jth
* element of this array represents the presence of universe[64*j +i]
* in this set.
*/
private long elements[];
?
7
要素数が多くても重労働にならない
10. 序数で配列インデックス?(1)
?
料理のハーブを表すクラス Herb
public class Herb {
public enum Type { ANNUAL, PERENNIAL, BIENNIAL }
private final String name;
private final Type type;
...
}
...
Herb[] garden = ...;
?
// 庭園にあるハーブ
庭園内の植物で、種類ごとのハーブのセットを作りたい
?
10
ならば、種類をハーブのセットのインデックスにすればいいじゃない?
11. 実際作ってみる…
?
セットの配列と ordinal() を使用したインデックスで作ると
// 配列をインデックスするのに ordinal() を使用 – これはやってはいけない!
Set<Herb>[] herbsByType = // Type.ordinal() でインデックスされる
(Set<Herb>[]) new Set[Type.values().length]; // 配列はジェネリックスと互換性がない、警告が出る
for (int i = 0; i < herbsByType.length; i++)
herbsByType[i] = new HashSet<>();
// 配列アクセス時に正しいインデックス値を入れないと ArrayIndexOutOfBoundException をスローしてしまう
for (Herb h : garden)
herbsByType[h.type().ordinal()].add(h);
?
enum をキーにして EnumMap で作ると
// データを enum と関連付けるために EnumMap を使用
EnumMap<Type, Set<Herb>> herbsByType =
new EnumMap<>(Type.class); // 実行時ジェネリック型情報はキー型の Class オブジェクトで提供
for (Type t : Type.values())
herbsByType.put(t, new HashSet<Herb>());
for (Herb h : garden)
herbsByType.get(h.type()).add(h);
11
// インデックスの境界に気にする必要ないほか、キーの型チェックもある