Hatena::ブログ(Diary)

Diary of Chiharu - Chiharu の日記

2018-08-13

赤城あんな、らいぶ

キラッとプリ☆チャンより赤城あんな。pixiv Sketch ライブ配信で描きました。娘(8 歳)のリクエストに応えてみたのですが、描き終えた頃には娘はイラストへの興味をなくしていたようでした。諸行無常です。いくら描いても終わらないフリル薔薇トラウマになりそうでしたが、頑張って描きました :-D

f:id:chiharunpo:20180813192520j:image

2018-08-11

いつもの姉妹らいぶ

いつもの姉妹を pixiv Sketch ライブ配信で描いてみました。久しぶりでしたが、やはり見られていると思うと緊張しますね。結局、配信後に気になるところをたくさん直しました。配信時点よりも姉のパースがマシになっていると思います :-D

f:id:chiharunpo:20180812002810j:image

2018-08-04

いつもの姉みずぎ

いつもの、姉の方。この夏の暑さのせいか、ペンタブの調子が悪く、ラフにざっと着色しました。しかし、今時の水着はパーカーだったりラッシュガードだったりして、見た目が普段着とあまり変わらないですよね。トレンドを踏襲するべきか迷いましたが、姉の方には脱いでもらいました :-D

f:id:chiharunpo:20180805005832j:image

バリアントの配列

バリアントの配列を文字列から生成して遊んでみました。テンプレートを使うと型情報による switch & case がなくて気持ちいいですね。C++17 以降の環境なら Variant には std::variant<> を使うべきでしょうけれども。

#include <string>
#include <sstream>
#include <vector>
#include <memory>
#include <stdexcept>

// boost::lexical_cast<> みたいなもの
struct Lexer {
 
 template <class Type>
 static Type to(const std::string& string)
 {
  std::stringstream stream(string);
  Type value;
  
  stream >> value;
  if (stream.fail() || stream.peek() != std::stringstream::traits_type::eof()) {
   throw std::runtime_error("Type missmatch error");
  }
  
  return value;
 }
 
};

template <>
bool Lexer::to<bool>(const std::string& string)
{
 std::stringstream stream(string);
 bool value;
 
 stream >> std::boolalpha >> value;
 if (stream.fail()) {
  switch (to<int>(string)) {
  case 0:
   value = false;
   break;
   
  case 1:
   value = true;
   break;
   
  default:
   throw std::runtime_error("Type missmatch error");
  }
 }
 
 return value;
}

// TODO : int, float を特殊化して stol, stof で最適化する。

// 任意の型のデータ
struct Variant {
 
 template <class Type> void set(Type value) = delete;
 template <class Type> decltype(auto) get() const = delete; // いずれ参照も返す
 
private:
 enum class Type {
  boolean, integer, real
 } type = Type::boolean;
 
 union {
  bool boolean = false;
  int integer;
  float real;
 };
 
 void validate(Type target) const
 {
  if (type != target) {
   throw std::runtime_error("Type missmatch error");
  }
 }
 
};

template <> void Variant::set<bool>(bool value) { type = Type::boolean, boolean = value; }
template <> void Variant::set<int>(int value) { type = Type::integer, integer = value; }
template <> void Variant::set<float>(float value) { type = Type::real, real = value; }

template <> decltype(auto) Variant::get<bool>() const { validate(Type::boolean); return boolean; }
template <> decltype(auto) Variant::get<int>() const { validate(Type::integer); return integer; }
template <> decltype(auto) Variant::get<float>() const { validate(Type::real); return real; }

// 任意の型のデータ配列
class VariableArray {
 
private:
 explicit VariableArray(std::vector<Variant>&& converted):
  array(std::move(converted))
 {
 }
 
public:
 auto& get(std::size_t index) const { return array[index]; }
 auto size() const { return array.size(); }
 
public:
 template <class Type>
 static std::shared_ptr<VariableArray> create(const std::vector<std::string>& source)
 {
  std::vector<Variant> converted;
  for (auto& item : source) {
   converted.emplace_back();
   converted.back().set(Lexer::to<Type>(item));
  }
  
  struct VariableArrayHelper : public VariableArray {
   VariableArrayHelper(std::vector<Variant>&& converted):
    VariableArray(std::move(converted)) {}
  };
  auto instance = std::make_shared<VariableArrayHelper>(std::move(converted));
  return std::move(instance);
 }
 
private:
 std::vector<Variant> array;
 
};

// テスト
#include <cassert>

int main(int argc, char* argv[])
{
 // boolean
 auto barray = VariableArray::create<bool>({ "true", "false", "1", "0" });
 assert(barray->size() == 4);
 assert(barray->get(0).get<bool>() == true);
 assert(barray->get(1).get<bool>() == false);
 assert(barray->get(2).get<bool>() == true);
 assert(barray->get(3).get<bool>() == false);
 
 auto exception_occured = false;
 try {
  barray->get(0).get<int>();
 } catch (std::exception& ex) {
  exception_occured = true;
 }
 
 assert(exception_occured);
 
 // integer
 auto iarray = VariableArray::create<int>({ "50", "34" });
 assert(iarray->size() == 2);
 assert(iarray->get(0).get<int>() == 50);
 assert(iarray->get(1).get<int>() == 34);
 
 exception_occured = false;
 try {
  iarray->get(0).get<bool>();
 } catch (std::exception& ex) {
  exception_occured = true;
 }
 
 assert(exception_occured);
 
 // real
 auto farray = VariableArray::create<float>({ "50", "34.2" });
 assert(farray->size() == 2);
 assert(farray->get(0).get<float>() == 50.f);
 assert(farray->get(1).get<float>() == 34.2f);
 
 exception_occured = false;
 try {
  farray->get(0).get<bool>();
 } catch (std::exception& ex) {
  exception_occured = true;
 }
 
 assert(exception_occured);
 
 return 0;
}

2018-07-29

いつもの。新顔ちゃんじゃんぷ

いつもの。新顔ちゃん。とある資料の挿絵のために描きました。子供の読書感想文の合間に描いたので、スケジュール的にキツかったですが、何とか日を越える前に仕上がりました。よかったよかった。

なお、読書感想文はまだ終わっていない模様です。あとは相方に任せました :-D

f:id:chiharunpo:20180729235110j:image

2018-07-22

はたらく血小板

はたらく細胞より血小板。さいっぼー、さいっぼー。我が家に、はたらく細胞ブーム到来。家族で毎週見てます :-D 血小板ちゃんは癒しですね。

f:id:chiharunpo:20180722160356j:image