So-net無料ブログ作成
前の10件 | -

【雑記】 どのプログラミング言語を学ぶべきか? [雑記]

的な記事を「稀に良く」目にするけど、実際に悩むことはないと思う。
なぜなら仕事で使う言語を選ぶだけだからさ(´・ω・`)
言語を選べるポジンションに下っ端がなることは余りないので、
下っ端は言語選択に悩むことはないのだ。
せいぜいパッチ(patch)やバッチ(batch)のスクリプト言語どうしよかぁ位よね。

学生だったらテストに出る奴やっとけばええんやで(´・ω・`)
え?働く前に予習しときたい?
遊べるときには遊んどこうよ(´・ω・`)

とか言ってたら話が終わってしまうので、敢えて勉強するなら前述のスクリプト言語をやっとくといい。
中でも個人的に推したいのはシェル(bash, zsh)かPerlだ。
えー人気言語ランキングにも出てこないレガシーうんこじゃーん。
てか、そいつらを言語っていうのも憚られるよね、だっさーい。
…とか思われるかもしれないけど、結局本格的な言語の起動スクリプトとして使ったり、
前述のパッチやバッチを作ったり、自分用の便利ツール作ったりと実作業よりちょっと外の作業でも
活躍するのですよ。
特にPerlなんかは文字列操作がめちゃくそ便利なので上手く使うと仕事が捗るのです(´・ω・`)
(ただワンライナーとかやりだすとゲテモノPGが出来上がるから注意ね)

パッチ(patch)の例だとシェルからPL/SQLに連携して、クソデータをささっと潰せるとかっこE。
きっとモテモテ間違いなし。上司のおっさんから。

え?決まった仕事がオープン系やWeb系でLinux処理系なんて使わない?
ハハ、そいつぁ参ったな(´・ω・`)
やっぱ無駄な勉強はやめて遊べるときは遊んどこうぜ!


【追記】
Web系で思い出したけどJavaScriptもいいよなぁ。。。

コメント(0) 
共通テーマ:資格・学び

【C】 とりあえず開発環境を [C言語]

ソネブロじゃソースコード書けねぇよクソが…的なことを前書いた気がするけど
リッチテキストモードなら書けるようだ。
馬鹿にしてごめんな。むしろ私が馬鹿だったよ(´・ω・`)
以前の記事も気が向いたら書き直そうかな。でもJavaの記憶も薄れつつあるからな!(悲しい)
【追記】
結局、リッチテキストモードも面倒臭かったので、
他のblogを参考にノーマルモードでpreタグ使って編集することにした。

とりあえず家のPCでもCの開発環境を作ることにした。
いつでも勉強できるぞ!!
…まぁ面倒臭がりな私は環境作ったら満足して終わるんだけどな!

さてセットアップの方法ですが、「モダンC言語プログラミング」ではわざわざXubuntu(マニアックな…)を
VirtualBox上で動かして、その上でEclipseを使っていましたが、
今のご時勢MinGWという便利なものがあるのでそこまでやる必要はない…と思う。
仮想環境だとやっぱりちょっと動作が重いし、コピペも面倒だし(出来ないことはないけどちょっと面倒)で、
やはり直接Windows上に作るほうが良かろう。
Torrentみたいなp2pを今時使うのもアレだしね。

細かいセットアップはググれば出てくるので、ここでは書かない。(何の為の記事だこれ)
MinGWは「developer-toolkit」「base」「msys-base」「g++」が入ってればOKだと思う。
実際のCコンパイラ(C++も兼用かな)はg++でmsysはmakefile等のビルドツールやdiff等の基本コマンドが入っているようだ。
toolkitとbaseは良く分からんがまぁベースなんだろう。(ぉぃ)
という訳で「MinGW\bin」と「MinGW\msys\1.0\bin」の両方ともパスを通しておく必要があるぞ。

後はEclipseのC/C++を展開するだけの簡単な作業。
日本語にしたいならPleiadesも突っ込む。
私はマニアなのでAll in Oneは使わないけど(重いの嫌い)、楽したいときはAll in Oneが良いでしょう。
Eclipseの公式サイトもクソ分かり難い事だしな!

早速簡単なプログラムを書いてみたけど、Eclipseがエラーで落ちたりしてヤバい。
いや、単にコーディングをミスってただけだけど(笑)
いやぁ、簡単にメモリぶっ壊して変な落ち方してくれるんだなぁ。流石C言語だぜ。
この面倒くささよ。。。
コメント(0) 
共通テーマ:資格・学び

【C】 C言語やることになったでござる… [C言語]

たまにはこちらの記事も投下しとかなきゃ(使命感)←無いです
と言ってもタイトルで完結しているのですが(笑)

新しいお仕事はC言語がメインのお仕事になりました。
通信系なのでとにかく速さ命のようです。となると確かにCになりますわな。

でもC言語は読んだことは有るけど書いたことは殆どない(´・ω・`)
という訳でまずは入門書を漁ってみたのでその感想でも。

■苦しんで覚えるC言語
https://9cguide.appspot.com/
こちらのサイトをそのまま書籍化した本ですね。
内容的にはC言語入門ですが、読む程度は出来る = ある程度知識はある訳で
タイトル的にもうちょっと中級な内容に踏み込んでるかな?
と思っていたらそんなことは無かったでござる。
という訳でわざわざ書籍を買う必要もなかったかな…と
ちゃんと調べてから買えよ!!(笑)

まぁ私には不要でしたが、
これからC言語を始めよう+敢えて紙で欲しいって方にはかなり良い書籍なのではないかと思います。
うざい位細かく説明してくれてるからね。


■プログラミング言語C 第二版
C言語の鉄板テキスト(笑)
昔買った記憶がうっすら有るけど引越しで技術本全部捨てたので再?購入。
訳が若干キツイところが有るけどEffective Javaとかプログラミング言語Javaとかに比べたら
全然読めるレベル。(※)
こちらも入門的な内容がメインだが4章以降でディープな内容にも踏み込むし、
やや言語記法等に今ではNGとされているような古い表現が見られたりするので、
読む方にもそれなりのレベルが要求される。
一通り学んでちょっとした実務をこなした後に復習用として読むといいと思う。


Effective Java、プログラミング言語Javaは内容的には素晴らしいのにクソ翻訳で台無しになって最悪ですね。
ちなみに翻訳の人はSo-netブログやっててビックリしましたね。
それでも敢えて言わせて貰おう。クソ翻訳であると。
こんなんで金とんなやボケが…と声を大にして言いたい。


■新・明解 C言語 実践編
実はまだあんまり読めていない(笑)
ある程度踏み込んだ情報が欲しくて購入した。
内容的には主にQA形式が取られているようで、私の要求を満たしてくれそうである。
とにかくCによる中~大規模プログラミングの経験が無いので
特に6章の関数の定義と宣言、11章のライブラリの開発辺りが役に立つのではと思って購入した次第。


■モダンC言語プログラミング
レガシーな言語であるCをIDE等を上手く活用してモダンにしましょう的な内容。
なかなか目の付け所が良いと思います。そういう応用情報こそ欲している訳です。
まぁC言語でオブジェクト指向とか無理があるのでこの辺は読み飛ばしが確定していますが(笑)
IDE、自動テスト、CIサーバ辺りはかなり興味深い。
Javaでやってんだから分かるだろ!という弁もあるかと思うが、
こうやってC言語での例が目に見える形であるというのはやはり良いものかと思うのですよ。
仮にもっといい方法があるとしても、その為の気付き源になるわけですし。


てな感じで今はプログラミング言語C 第二版をメインに読み込んでいます。
言語仕様の再確認的なね。
型がどうだの、制御文がどうだのは幾らでもWebに転がってるからどうでもいいんですけど、
問題はその先ですよね。
関数の組み合わせ方やら何やらのちょっと大きい視点での情報が欲しいんですが、
そういうのはなかなか転がってないんだよなぁ。
(この辺はどの言語でも同じですが)

ただ、エラーやバグ情報等の「つまずき」に関してはStack Over Flow等のサイトのお陰で大分良くなりましたね。
凄く役に立ちます。
コメント(0) 
共通テーマ:資格・学び

【Java】 Stream API 勉強中 (補足) [Java]

> entryArchiveのところで例外食いつぶしてますが、もちろんワザとです。

試しに例外をthrow(s)するようにしたところ、コンパイルが通らないことが判明。
いつもの「キャッチしろよクソボケが!」と怒られちゃう。
あぁ、forEachが例外に対してなーんもしてくれないからかな?

色んなブログなんかを舐め回したところentryArchiveをブロックで囲んでtry-catchしないとイケナイらしい。
うっは、これは面倒くさいし、見難いし醜い。
もしくはRuntimeExceptionに包むしかないと。

まぁでもファイル出力をStreamに噛ますのが邪道なのかもしれないしなぁ。
副作用だか何だかで。
てかIOと副作用の関係性も謎だけど。(近いうちに真面目に調べよう。。。)
あとまぁ例外をcatchせなならんことがどれ位有るかって話よなぁ。
(個人的に)例外は極力避ける方針だからまぁ余り問題は出ないとは思うけれども。

C言語なんかは例外無い訳だから戻り値で頑張ろうと思えば出来るんでしょうし、
「例外っていらなくね?」って論に転じるのも有りか?
(いや、APIが例外指向になっちゃってる時点で無いな…)
コメント(0) 
共通テーマ:資格・学び

【Java】 Stream API 勉強中 (ソース) [Java]

package application;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Arrays;
import java.util.function.Predicate;
import java.util.stream.Stream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

public class FileManager {
    
    private static final Logger log = LogManager.getLogger(FileManager.class);
    private Path rootpath;
    
    public static void main(String[] args) {
        
        Path filepath = Paths.get("E:/RootDir");
        FileManager fmanager = new FileManager(filepath);
        
        Path zippath = Paths.get("E:/DestDir/save.zip");
        String[] subdirs = {"subdir1", "subdir2"};
        
        fmanager.packageOut(subdirs, zippath);
    }
    
    public FileManager(Path path) {
        rootpath = path;
    }
    
    
    public void packageOut(String[] subdirs, Path zippath) {
        
        Path[] targets = Arrays.stream(subdirs).map(subdir -> rootpath.resolve(subdir)).toArray(Path[]::new);
        Predicate<Path> selecter = path -> Arrays.stream(targets).anyMatch(target -> path.startsWith(target));
        
        try (
            Stream<Path> stream = Files.walk(rootpath);
            ZipOutputStream zos = new ZipOutputStream(new BufferedOutputStream(Files.newOutputStream(zippath)));
        ) {
            stream.filter(Files::isRegularFile).filter(selecter::test).forEach(path -> entryArchive(zos, path));
        } catch(IOException e) {
            log.error("圧縮に失敗しました。");
            throw new Error(e);
        }
    }
    
    
    private void entryArchive(ZipOutputStream zos, Path target) {
        
        String entryName = rootpath.relativize(target).toString();
        ZipEntry entry = new ZipEntry(entryName);
        
        try (BufferedInputStream is = new BufferedInputStream(Files.newInputStream(target));) {
            
            zos.putNextEntry(entry);
            
            byte[] buf = new byte[1024];
            int len = 0;
            
            while ((len = is.read(buf)) != -1) {
                zos.write(buf, 0, len);
            }
            
            zos.closeEntry();
            
        } catch (IOException e) {
            log.error("エントリ[{}]の圧縮に失敗しました。", entryName);
            e.printStackTrace();
        }
    }
}

コメント(0) 
共通テーマ:資格・学び

【Java】 Stream API 勉強中 [Java]

Streamやらラムダ式やらを勉強中。

正直な話、「関数型」についてはあんまりピンと来なかったっていうか、
なんか馬鹿げた論争とか有ってシラけたのでやる気ゼロになってしまった訳ですけれども、
こと「関数を扱う」という指向と言いますか、集合指向と言いますか、
については大いに感じ入る所が有ります。

この辺りイマイチ、ピンと来ない方も居られるかもしれませんが、
集合を扱うとか、コマンドラインのパイプ処理とか、Perlのワンライナー辺りをイメージすると
結構理解が早かったりしますね。
…逆に混乱するかも分からんけど(笑)

とりあえず勉強の一環で
「あるディレクトリをフィールドとして持ち、そのディレクトリを(とある目的で)管理するクラス」
というのを個人的に作っていてですね、
その機能の一部である、「自身のサブディレクトリの幾つかをZipで出力する」機能をリファクタリングしてみました。

例での使い方はE:/RootDirの下にsubdir1~nまで有る内の2つをZip圧縮しています。
元のソース(※)からすると大分スッキリした感じですが、もうちょっと何とか出来そうな気もしています。

※ 元のソースは面倒なんで載せませんっていうか、ローカルに持ってないのです。

関数型インターフェイスの実装をメソッドに渡して別の関数型実装とクロスさせて使ったりするのが
本領だと思うんですがそこまでは至ってないですね。
まぁ昨日今日の突貫知識なので許してちょ。

entryArchiveのところで例外食いつぶしてますが、もちろんワザとです。
圧縮出来るものだけ圧縮するイメージですね。
もちろん一個失敗したらもう止めってのも良いと思いますけど、この場合はそんな必要もないかなと。
(失敗する可能性も低いでしょうし、失敗する場合は全部失敗するでしょう。)
本気でやるならゴミを削除する処理とかも必要でしょうかね。。。

ただこのStream APIですけど、やはりワンライナーよろしくやり過ぎると可読性が一気に下がります。
第三者から見たら何やってんだかさっぱり分からなくなる訳ですね。
その辺のバランス感覚を保ちつつ程々で手を打つのがポイントかと思います。


ソースは長くなったので次の記事で。
(ソネブロのうんこ仕様により一部全角となっております)
コメント(0) 
共通テーマ:資格・学び

【Java】 例外は難しい ⑤ [Java]

さて、長い間が空いてしまって結局何書きたかったのかすっかり忘れてしまった訳ですが。。。

結局、例外はどうさばけば良いか?という話ですが(強引に戻したっ)
「例外は極力書かない、書かさない」
これな。

まぁその名の如く例外というはやはり例外的な処理な訳ですから、
やたらめったら書くような機会があるのは多分設計が良くない…という話に落ち着くのではないかと。
だからといって使うのに萎縮してしまうのも、それはそれで違う訳なので勘違いされたくはないのですが。


■例外を使わざるを得ないポイント

① APIが検査例外をthrowする場合。
まぁ良くあるのはIO例外とSQL例外ですな。Web系なら…うーん忘れた(笑)
最近はバッチマンですからな!ハハハ。
(IO例外とSQL例外については別途記事を上げるかもしれない。)

キャッチしたらリトライするってのも一つの考えですが、まぁそんな面倒なことしたくないですわな。(酷い)
なもんでバッチ系ならどうせ終わらせるしかないのでError、
Web系ならキャッチしてエラーページ出す場合が多いでしょうから例外サブクラスに包んでポイすれば良いかと。
(ちゃんと専用の例外クラスを作ると尚良いね)

あぁでもFileNotFoundExceptionはthrow(s)しても良いね。
これはデフォルト設定なんかがある場合は対処しようがある。


② 成功・失敗を知らせる必要があるが戻り値をそれに使えない場合。
例えば良く例に出るログイン処理なんかの場合。
DBにユーザ情報が無かったFailed(※)とDBがぶっ壊れてそもそも問い合わせ出来なかったFailedは
明確に区別したい訳で。
片や再入力を促し、片やエラーページへ、みたいな。
そういうのは戻り値をbool値にしても判断できないし、数値(エラーコード)で返すって手も有るけど、
処理上、ログインチェックの戻りがユーザ情報だったりする場合は困っちゃいますね。
そういうときはやはり専用の例外を吐くとスッキリしたコードに出来そうです。

※ DBにユーザ情報が無かったFailedはそもそも正常処理(終了)であるので
  ユーザ情報有りの正常終了と判断がつかない…と言うべきかもしれない。

戻り値がプリミティブな場合も同じことが言えますね。
Integer.parseIntのNumberFormatExceptionの例がそのまんまですが、
これでエラーなら-1を返すとかやってしまうと変換された正しい-1なのか何なのか?と。

とは言え、これは使う側との約束(※)がしっかりしていれば発生しない場合もあるので、
極力そのお約束を文書化するなりして無くす方向に持って行きたいですね。
parseIntに数値を表す文字以外は渡すなよ…と。
(やはりチェックメソッド欲しいよなぁ。。。)

※ 例えばparseInt(に近い処理)の場合は変な数値は0に丸めますよ…と言ったルールを明文化できれば
  RuntimeExceptionを吐く必要すらない筈です。
  (公に使うAPIでそんな丸めが許される訳はないのでInteger.parseIntはRuntimeExceptionで正しい)


③ その他
なんかあるかもしれない。
まぁ予防線だ。ハハハ。
コメント(0) 
共通テーマ:資格・学び

【Java】 例外は難しい ④ [Java]

…といった辺りの論議も実に数年前からなされていたりする訳ですけれども、
IBMさんの文書
https://www.ibm.com/developerworks/jp/java/library/j-jtp05254/
でもやはり当初は「例外はキャッチして回復すべし」…が基本であったことが述べられてますね。

つまり良く見るコード
 public static void main(String[] args) throws Exception {
   ……
 }

は宜しくなかった訳です。敢えてこれを表現するなら

 public static void main(String[] args) {
  try {
   ……
  } catch (XxxException e) {
   System.exit(1);
  }
 }

という風にキャッチして「正常に」エラーコードを返すのが基本であった(過去形)と。
(ちなみに私は上の書き方を否定しません)


【歴史的な流れ(半分位憶測)】
Exceptionは「全て」キャッチして回復すべし!

いやいや、何だかtry-catchだらけで面倒くせーし、コードもきったないんですけどー

事前にチェックできるもんは、免除していいんじゃね?
よっしゃ、RuntimeException作ったろ!

うっは、これ便利すわ。
寧ろチェック例外が要らんかったんや!!

いやいや、ちょっと待って、チェック例外はチェック例外で有用だよ?

(´・ω・`)

という訳で結局どうすれバインダー。

超個人的な意見を言わせて頂くとですね、そもそも例外が要らないんです(´・ω・`)
だって知りたいのは処理がコケたかコケなかっただけじゃん。
Errorが有れば充分じゃないか?えぇ?

…と声高に言うと方々から反発を喰らいそうなので、これは心に仕舞っといてですね、
(割と本気で思ってはいる訳ですが)
「キャッチすべきではない重大な問題」であるErrorと「キャッチして回復」するExceptionの両極端だったのが、
やはり失敗だったんですね。
つまり「回復不能なあまり重要でもない問題」という考え方がすっぽ抜けてる。
(っていうかそれは美しくないと考えられたのだろう)
でも「回復不能なあまり重要でもない問題」って絶対有るんですよ。
例えばIOExceptionとかIOExceptionとかIOExceptionとかIOExceptionな。
(この話は後でする…筈)

で、現状それに対してウザさ解消だけの為に後付けやっつけで追加されたような
RuntimeExceptionを使っている訳です。ハッキリ言って訳が分からないよ!!
Errorだろそれ?Errorだるぉぉぉぉぐわぁぁぁぁぁっ!!!
…と言いたくなるもんです。

っていうかねErrorは「重大な問題」であって「VMの問題」なんて一言も述べられてないのに
VMエラーにしか使ったらダメという通説がまかり通ってしまったのがまぁ不幸ですわな。
コメント(0) 
共通テーマ:資格・学び

【Java】 例外は難しい ③ [Java]

さて、ここで一つ、例外に関する処理を見てみたい。

 String strnum = [何らかの処理];
 int intnum = 0;
 try {
  intnum = Integer.parseInt(strnum);
 } catch (NumberFormatException e) {
  intnum = -1;
 }

果たしてこれは有りなのだろうか?
正直な話、私はこういうコードを書いたことが有る。
なぜなら「例外はキャッチして復帰すべき」と考えていたからだ。
そう、「例外は難しい ①」だけを読めばこの考え方は正しいと思う。

が、NumberFormatExceptionはRuntimeExceptionのサブクラスである。
「プログラマが発生しないことを確信できる」から強制的にキャッチやthrows節に書くことを免除されているのだ。
parseIntの説明にも「文字列内の文字はすべて、10進数の桁である必要があります。」と明示されている。
であれば、

 String strnum = [何らかの処理];
 [strnumが10進数であることをチェックする処理]
 int intnum = Integer.parseInt(strnum);

とするのがより良いようにも思える。
[strnumが10進数であることをチェックする処理]により「プログラマが発生しないことを確信できる」状態にする訳です。
さらにstrnum = [何らかの処理]の処理で10進数の整数を表現する文字列が確信できるのであれば

 String strnum = [何らかの処理];
 int intnum = Integer.parseInt(strnum);

でも問題ない訳です。
…のですが、、、
RuntimeExceptionがキャッチまたはthrows説に書くことがコンパイラに検査されない、というのは
キャッチすることが禁止されている…という訳ではないですよね。
なので「例外はキャッチして復帰すべき」という考え方も間違っているとは言いきれないのです。
上記3つのパターンのどれが最善かは最早前後の処理や規約で判断するしかなく、
これが例外をして難しいと言わしめる原因になっているのでは?と考える次第です。

個人的な見解としては、
NumberFormatExceptionは検査例外、つまり通常のExceptionのサブクラスであるべきだったのでは?と。
もしくはRuntimeExceptionであるのであれば、Integerに値検査用のメソッドがあるべきだったのでは?
と思う訳ですが、残念ながらそうはなっていないですね。

ちなみにintnumが復帰することが許されない…という状況も充分有りうるので1番目と2番目の処理において
チェックに違反した場合はErrorをスローすることも有り得るのかな…と。
コメント(0) 
共通テーマ:資格・学び

【Java】 例外は難しい ② [Java]

さて、前回でほぼ例外の仕様面は分かったような気になる訳ですが、
Error以外にもコンパイラの検査を免れる奴が居るらしいですぞ。

> 尚、Errorと『RuntimeException』およびそれらのサブクラス以外は
> コンパイラにより例外チェック機構が走り、

そう、RuntimeExceptionとそのサブクラスも検査を免れるのです!
なんということでしょう!!

なぜRuntimeExceptionは検査を免れるのだろうか?

プログラマには発生しないことが確信できるのに、
いちいち処置を強制させるのはお互いの得にならない…ということのようだ。
(この辺英語が難しくてちょっと良く分からないけど。。。)

例えばNullPointerExceptionならNullチェックをしておけば発生しないし、
NumberFormatExceptionなら数値の範囲チェックをすれば発生しない。

まぁそれはそれとして、そもそもRuntimeExceptionとは何なのだろうか?
直訳すると実行時例外となる訳ですが、実行時に発生する…ってことならほぼ全部そうだよなと(笑)
RuntimeExceptionの説明を見てもExceptionと違ってチェックされませんよ位のものである。
うーむ、解せぬ!

なぜRuntimeExceptionという名前を付けたのだろうか?
名前をつけるならUncheckedExceptionではないのか?
もっと言うとThrowableの直下に置くべきではないのか?

といった疑問が沸く訳ですが、この疑問、晴れる事は無さそうです。

単純に事前の入力値チェック等で充分に回避可能であればRuntimeExceptionのサブクラスにすることで
コンパイラの検査を回避出来ますよ、煩わしくないでしょ?
…的なものであって深い意味は無さそうである。
Exceptionのサブクラスであるところからして後付け感も感じる訳でして。。。



【参考】
https://docs.oracle.com/javase/jp/8/docs/api/
https://docs.oracle.com/javase/specs/jls/se8/html/jls-11.html
コメント(0) 
共通テーマ:資格・学び
前の10件 | -