# dplyr コードリーディングガイドライン

## はじめに

このガイドラインは、dplyrのコードベースを効率的に理解するための手引きです。
R言語に精通していないエンジニアでも、段階的に学習できるよう構成されています。

**対象読者:**
- プロジェクトに新規参画するエンジニア
- 他言語からの経験者
- コードレビューを行う担当者

**dplyrとは:**
dplyrは「データ操作の文法(A Grammar of Data Manipulation)」を提供するRパッケージです。データフレームに対する一貫した操作セット（verb）を提供し、データ分析のワークフローを効率化します。

---

## 1. 言語基礎

> このセクションでは、R言語の基本構文と概念を解説します。

### 1.1 プログラム構造

Rは関数型プログラミング言語であり、すべての操作は関数として表現されます。dplyrでは、S3ジェネリック関数とR6クラスを組み合わせたアーキテクチャを採用しています。

**S3ジェネリック関数の例** (`R/mutate.R:145-147`)
```r
mutate <- function(.data, ...) {
  UseMethod("mutate")
}
```

**R6クラスの例** (`R/data-mask.R:1-10`)
```r
DataMask <- R6Class(
  "DataMask",
  public = list(
    initialize = function(data, by, verb, error_call) {
      rows <- by$data$.rows
      # ...
    }
  )
)
```

### 1.2 データ型と変数

dplyrでは以下のデータ型が頻繁に使用されます:

| データ型 | 説明 | 例 |
|---------|------|-----|
| `data.frame` | 基本的なデータフレーム | `data.frame(x = 1:3, y = c("a", "b", "c"))` |
| `tibble` | 拡張データフレーム | `tibble(x = 1:3)` |
| `grouped_df` | グループ化されたデータフレーム | `group_by(df, col)` |
| `rowwise_df` | 行単位の操作用データフレーム | `rowwise(df)` |
| `quosure` | 遅延評価式 | `enquo(expr)` |

**データ型の定義例** (`R/grouped-df.R:18-32`)
```r
grouped_df <- function(data, vars, drop = group_by_drop_default(data)) {
  if (!is.data.frame(data)) {
    abort("`data` must be a data frame.")
  }
  if (!is.character(vars)) {
    abort("`vars` must be a character vector.")
  }

  if (length(vars) == 0) {
    as_tibble(data)
  } else {
    groups <- compute_groups(data, vars, drop = drop)
    new_grouped_df(data, groups)
  }
}
```

### 1.3 制御構造

Rの制御構造は他の言語と類似していますが、ベクトル化操作が推奨されます。

**条件分岐の例** (`R/mutate.R:237-250`)
```r
if (keep == "all") {
  names_out <- names
} else {
  names_keep <- switch(
    keep,
    used = names(used)[used],
    unused = names(used)[!used],
    none = character(),
    abort("Unknown `keep`.", .internal = TRUE)
  )
  names_out <- intersect(names, c(names_new, names_groups, names_keep))
}
```

**ループの例** (`R/mutate.R:271-276`)
```r
for (i in seq_along(dots)) {
  poke_error_context(dots, i, mask = mask)
  context_poke("column", old_current_column)

  new_columns <- mutate_col(dots[[i]], data, mask, new_columns)
}
```

### 1.4 関数/メソッド定義

Rの関数定義は `function()` キーワードを使用します。dplyrではS3メソッドディスパッチを多用しています。

**S3メソッドの定義例** (`R/filter.R:231-239`)
```r
#' @export
filter.data.frame <- function(.data, ..., .by = NULL, .preserve = FALSE) {
  filter_impl(
    .data = .data,
    ...,
    .by = {{ .by }},
    .preserve = .preserve,
    .verb = "filter"
  )
}
```

**内部ヘルパー関数の例** (`R/arrange.R:101-187`)
```r
arrange_rows <- function(data, dots, locale, error_call = caller_env()) {
  dplyr_local_error_call(error_call)

  size <- nrow(data)
  # ... 内部処理
  vec_order_radix(
    x = data,
    direction = directions,
    na_value = na_values,
    chr_proxy_collate = chr_proxy_collate
  )
}
```

### 1.5 モジュール/インポート

dplyrは `NAMESPACE` ファイルでインポート/エクスポートを管理します。roxygen2によるドキュメント生成と連携しています。

**NAMESPACEの構造** (`NAMESPACE:440-451`)
```r
import(rlang)
import(vctrs, except = data_frame)
importFrom(R6,R6Class)
importFrom(generics,intersect)
importFrom(glue,glue)
importFrom(lifecycle,deprecated)
importFrom(magrittr,"%>%")
importFrom(tibble,as_tibble)
importFrom(tidyselect,all_of)
```

**パッケージ内でのインポート使用例** (`R/mutate.R:183`)
```r
cols <- mutate_cols(.data, dplyr_quosures(...), by)
```

---

## 2. プロジェクト固有の概念

> このセクションでは、dplyr特有の概念を解説します。

### 2.1 フレームワーク固有の概念

#### Data Masking（データマスキング）

dplyrの中核概念の一つ。ユーザーがデータフレームの列名を直接参照できるようにする仕組みです。

**DataMaskクラス** (`R/data-mask.R:1-50`)
```r
DataMask <- R6Class(
  "DataMask",
  public = list(
    initialize = function(data, by, verb, error_call) {
      # ...
      private$chops <- .Call(
        dplyr_lazy_vec_chop_impl,
        data,
        rows,
        private$env_current_group_info,
        private$grouped,
        private$rowwise
      )
    }
  )
)
```

#### Tidy Evaluation（tidyeval）

rlangパッケージによる遅延評価システム。`enquo()`, `!!`, `{{ }}` などの演算子を使用します。

**tidyevalの使用例** (`R/group-by.R:148-154`)
```r
group_by.data.frame <- function(
  .data,
  ...,
  .add = FALSE,
  .drop = group_by_drop_default(.data)
) {
  groups <- group_by_prepare(.data, ..., .add = .add, error_call = current_env())
  grouped_df(groups$data, groups$group_names, .drop)
}
```

### 2.2 プロジェクト独自のパターン

#### Verbパターン

dplyrは「動詞（verb）」と呼ばれる関数群を中心に設計されています。

| Verb | 目的 | ファイル |
|------|------|---------|
| `mutate()` | 列の追加・変更 | `R/mutate.R` |
| `filter()` | 行のフィルタリング | `R/filter.R` |
| `select()` | 列の選択 | `R/select.R` |
| `arrange()` | 行のソート | `R/arrange.R` |
| `summarise()` | グループごとの集計 | `R/summarise.R` |
| `group_by()` | グループ化 | `R/group-by.R` |

#### by引数パターン

dplyr 1.1.0以降、`.by`引数を使用したper-operation groupingをサポートしています。

**byパターンの使用例** (`R/filter.R:265-271`)
```r
by <- compute_by(
  by = {{ .by }},
  data = .data,
  by_arg = ".by",
  data_arg = ".data",
  error_call = .error_call
)
```

---

## 3. 命名規則

> このセクションでは、プロジェクト全体で使用される命名規則を解説します。

### 3.1 ファイル・ディレクトリ命名

| パターン | 意味 | 例 |
|---------|------|-----|
| `{verb}.R` | 主要なverb関数 | `mutate.R`, `filter.R`, `select.R` |
| `{verb}-{detail}.R` | verbの関連機能 | `join-by.R`, `join-cols.R`, `join-rows.R` |
| `colwise-{verb}.R` | 列方向操作（非推奨） | `colwise-mutate.R`, `colwise-filter.R` |
| `deprec-{feature}.R` | 非推奨機能 | `deprec-do.R`, `deprec-funs.R` |
| `defunct-{feature}.R` | 廃止機能 | `defunct-lazyeval.R` |
| `data-{name}.R` | データセット定義 | `data-starwars.R`, `data-storms.R` |
| `compat-{package}.R` | 互換性レイヤー | `compat-dbplyr.R` |
| `import-standalone-{feature}.R` | スタンドアロンインポート | `import-standalone-purrr.R` |

### 3.2 クラス・関数・変数命名

| プレフィックス/サフィックス | 意味 | 例 |
|---------------------------|------|-----|
| `dplyr_` | dplyr内部関数 | `dplyr_col_modify`, `dplyr_row_slice` |
| `check_` | 検証関数 | `check_filter`, `check_keep` |
| `compute_` | 計算関数 | `compute_by`, `compute_groups` |
| `.data` | 入力データフレーム引数 | `filter(.data, ...)` |
| `.by` | per-operation grouping引数 | `mutate(.data, .by = col)` |
| `_impl` | 実装詳細関数 | `filter_impl` |
| `_cols` | 列操作ヘルパー | `mutate_cols`, `summarise_cols` |
| `_rows` | 行操作ヘルパー | `filter_rows`, `join_rows` |
| `_df` | データフレームクラス | `grouped_df`, `rowwise_df` |

### 3.3 プログラム分類一覧

| 分類 | 説明 | ファイル例 |
|------|------|-----------|
| 主要verb | 単一テーブル操作 | `mutate.R`, `filter.R`, `select.R`, `arrange.R`, `summarise.R` |
| グループ操作 | グループ化関連 | `group-by.R`, `group-data.R`, `group-map.R`, `grouped-df.R` |
| 結合操作 | テーブル結合 | `join.R`, `join-by.R`, `join-cols.R`, `join-rows.R` |
| 集合操作 | 集合演算 | `sets.R` |
| 行操作 | 行単位処理 | `rows.R`, `rowwise.R`, `slice.R` |
| ユーティリティ | 共通機能 | `utils.R`, `context.R`, `conditions.R` |
| C++バインディング | 高速化実装 | `src/*.cpp` |

---

## 4. ディレクトリ構造

> このセクションでは、プロジェクトのディレクトリ構造を解説します。

```
dplyr-main/
├── R/                      # Rソースコード（約100ファイル）
│   ├── mutate.R            # mutate verb
│   ├── filter.R            # filter verb
│   ├── select.R            # select verb
│   ├── arrange.R           # arrange verb
│   ├── summarise.R         # summarise verb
│   ├── group-by.R          # group_by verb
│   ├── grouped-df.R        # grouped_dfクラス
│   ├── data-mask.R         # DataMask R6クラス
│   ├── join.R              # join関数群
│   └── ...
├── src/                    # C++ソースコード
│   ├── dplyr.h             # 共通ヘッダー
│   ├── init.cpp            # R/C++インターフェース初期化
│   ├── filter.cpp          # filter C++実装
│   ├── mutate.cpp          # mutate C++実装
│   ├── group_by.cpp        # group_by C++実装
│   ├── summarise.cpp       # summarise C++実装
│   └── ...
├── man/                    # Rdドキュメント（roxygen2生成）
├── tests/                  # テストコード
│   └── testthat/           # testthatテスト
├── vignettes/              # ビネット（チュートリアル）
├── data/                   # サンプルデータセット
├── data-raw/               # データ生成スクリプト
├── DESCRIPTION             # パッケージメタデータ
├── NAMESPACE               # エクスポート/インポート定義
└── README.md               # プロジェクト概要
```

### 各ディレクトリの役割

| ディレクトリ | 役割 | 主要ファイル |
|-------------|------|-------------|
| `R/` | Rソースコード | verb関数、クラス定義、ユーティリティ |
| `src/` | C++ソースコード | 高速化が必要な処理の実装 |
| `man/` | ドキュメント | roxygen2から自動生成されるRdファイル |
| `tests/testthat/` | 単体テスト | test-{機能}.R形式のテストファイル |
| `vignettes/` | チュートリアル | Rmarkdown形式のドキュメント |
| `data/` | 組み込みデータ | starwars、storms等のデータセット |

---

## 5. アーキテクチャ

> このセクションでは、プロジェクトのアーキテクチャパターンを解説します。

### 5.1 全体アーキテクチャ

dplyrは「S3ジェネリック + R6クラス + C++バックエンド」のハイブリッドアーキテクチャを採用しています。

```
┌─────────────────────────────────────────────────────────────┐
│                    ユーザーAPI層                              │
│  mutate() | filter() | select() | arrange() | summarise()   │
│               (S3ジェネリック関数)                            │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                   Data Masking層                             │
│                    DataMask R6クラス                          │
│     (tidyeval, quosure処理, グループ単位評価)                 │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                   バックエンド層                              │
│         vctrs | rlang | C++ (.Call)                         │
│      (高速ベクトル操作, メモリ効率化)                         │
└─────────────────────────────────────────────────────────────┘
                              │
                              ▼
┌─────────────────────────────────────────────────────────────┐
│                  データ層                                    │
│    data.frame | tibble | grouped_df | rowwise_df            │
└─────────────────────────────────────────────────────────────┘
```

### 5.2 レイヤー構成

| レイヤー | 責務 | 代表的なファイル |
|---------|------|-----------------|
| API層 | ユーザー向けインターフェース | `R/mutate.R`, `R/filter.R`, `R/select.R` |
| Data Masking層 | 遅延評価、グループ処理 | `R/data-mask.R`, `R/context.R` |
| バックエンド層 | 高速演算、型変換 | `src/*.cpp`, vctrsパッケージ |
| データ層 | データ構造の定義 | `R/grouped-df.R`, `R/rowwise.R` |

### 5.3 データフロー

典型的なverb呼び出しのデータフロー:

```
ユーザー呼び出し: df |> mutate(new_col = col1 + col2)
                              │
                              ▼
    ┌─────────────────────────────────────────┐
    │  1. S3ディスパッチ: mutate.data.frame   │
    │     (R/mutate.R:171-209)                │
    └─────────────────────────────────────────┘
                              │
                              ▼
    ┌─────────────────────────────────────────┐
    │  2. by引数の処理: compute_by()          │
    │     グループ化情報の取得                 │
    └─────────────────────────────────────────┘
                              │
                              ▼
    ┌─────────────────────────────────────────┐
    │  3. DataMask作成: DataMask$new()        │
    │     (R/data-mask.R)                     │
    │     - 列のchop（グループ分割）           │
    │     - バインディング環境作成            │
    └─────────────────────────────────────────┘
                              │
                              ▼
    ┌─────────────────────────────────────────┐
    │  4. 式の評価: mutate_cols()             │
    │     - quosureの展開                     │
    │     - グループごとの評価                │
    │     - 結果のunchop（結合）              │
    └─────────────────────────────────────────┘
                              │
                              ▼
    ┌─────────────────────────────────────────┐
    │  5. 結果の構築: dplyr_col_modify()      │
    │     - 列の追加/変更                     │
    │     - 属性の復元                        │
    └─────────────────────────────────────────┘
                              │
                              ▼
              結果データフレーム
```

---

## 6. 主要コンポーネント

> このセクションでは、主要なコンポーネントとその連携を解説します。

### 6.1 エントリーポイント

dplyrの各verbは、S3ジェネリック関数として定義され、`UseMethod()`でディスパッチされます。

**mutate()のエントリーポイント** (`R/mutate.R:145-147`)
```r
mutate <- function(.data, ...) {
  UseMethod("mutate")
}
```

**data.frameメソッド** (`R/mutate.R:171-209`)
```r
mutate.data.frame <- function(
  .data,
  ...,
  .by = NULL,
  .keep = c("all", "used", "unused", "none"),
  .before = NULL,
  .after = NULL
) {
  keep <- arg_match0(.keep, values = c("all", "used", "unused", "none"))

  by <- compute_by({{ .by }}, .data, by_arg = ".by", data_arg = ".data")

  cols <- mutate_cols(.data, dplyr_quosures(...), by)
  # ...
}
```

### 6.2 ビジネスロジック

#### DataMaskクラス

式の評価を管理するR6クラス。グループごとに式を評価し、結果を収集します。

**主要メソッド** (`R/data-mask.R`)
```r
# 式の評価
eval_all_mutate = function(quo) {
  eval <- function() .Call(`dplyr_mask_eval_all_mutate`, quo, private)
  eval()
}

# 列の追加
add_one = function(name, chunks, result) {
  .Call(`dplyr_mask_binding_add`, private, name, result, chunks)
}

# 現在のグループ情報取得
current_rows = function() {
  private$rows[[self$get_current_group_id_mutable()]]
}
```

#### verb処理関数

各verbには `_cols` または `_rows` サフィックスを持つヘルパー関数があります。

**mutate_cols()** (`R/mutate.R:253-301`)
```r
mutate_cols <- function(data, dots, by, error_call = caller_env()) {
  error_call <- dplyr_error_call(error_call)

  mask <- DataMask$new(data, by, "mutate", error_call = error_call)
  # ...
  withCallingHandlers(
    for (i in seq_along(dots)) {
      new_columns <- mutate_col(dots[[i]], data, mask, new_columns)
    },
    error = dplyr_error_handler(...),
    warning = dplyr_warning_handler(...)
  )
  # ...
}
```

### 6.3 データアクセス

#### グループ化データフレーム

`grouped_df`クラスはグループ情報を属性として保持します。

**grouped_dfの構造** (`R/grouped-df.R:139-157`)
```r
new_grouped_df <- function(x, groups, ..., class = character()) {
  if (!is.data.frame(x)) {
    abort("`x` must be a data frame.")
  }
  if (!is.data.frame(groups)) {
    abort("`groups` must be a data frame")
  }

  new_tibble(
    x,
    groups = groups,
    ...,
    nrow = NROW(x),
    class = c(class, "grouped_df")
  )
}
```

**グループデータの取得** (`R/group-data.R`)
```r
group_data(x)  # グループキーと行インデックスを含むデータフレーム
group_keys(x)  # グループキーのみ
group_rows(x)  # 行インデックスのみ
group_vars(x)  # グループ化変数名
```

### 6.4 ユーティリティ/共通機能

**dplyr_col_modify()** - 列の追加・変更を行う内部関数

**dplyr_row_slice()** - 行のスライスを行う内部関数

**dplyr_reconstruct()** - データフレームの属性を復元

---

## 7. よく使われるパターン

> このセクションでは、コード内で頻出するパターンを解説します。

### パターン一覧

| パターン | 説明 | 出現頻度 | 代表的なファイル |
|---------|------|---------|-----------------|
| S3ジェネリック | 型によるディスパッチ | 高 | 全verb |
| tidyeval | 遅延評価 | 高 | `data-mask.R` |
| withCallingHandlers | エラー/警告処理 | 高 | `mutate.R`, `filter.R` |
| .Call | C++呼び出し | 中 | `data-mask.R`, `grouped-df.R` |
| R6クラス | オブジェクト指向 | 低 | `data-mask.R` |

### 各パターンの詳細

#### パターン1: S3ジェネリック + UseMethod

**目的:** 異なるデータ型に対して統一したインターフェースを提供

**実装例:**
```r
// ファイル: R/filter.R:216-227
filter <- function(.data, ..., .by = NULL, .preserve = FALSE) {
  check_by_typo(...)
  check_not_both_by_and_preserve({{ .by }}, .preserve)
  UseMethod("filter")
}

// data.frame用メソッド
filter.data.frame <- function(.data, ..., .by = NULL, .preserve = FALSE) {
  filter_impl(.data = .data, ..., .by = {{ .by }}, .preserve = .preserve, .verb = "filter")
}
```

**解説:** `UseMethod("filter")`により、`.data`の型に応じて適切なメソッドが選択されます。

#### パターン2: tidyevalによる遅延評価

**目的:** ユーザーの式をデータフレームのコンテキストで評価

**実装例:**
```r
// ファイル: R/group-by.R:222
new_groups <- enquos(..., .ignore_empty = "all")
```

**解説:** `enquos()`で引数を遅延評価式（quosure）としてキャプチャし、後で評価します。

#### パターン3: withCallingHandlersによるエラー処理

**目的:** エラーや警告に追加情報を付加

**実装例:**
```r
// ファイル: R/mutate.R:270-289
withCallingHandlers(
  for (i in seq_along(dots)) {
    new_columns <- mutate_col(dots[[i]], data, mask, new_columns)
  },
  error = dplyr_error_handler(
    dots = dots,
    mask = mask,
    bullets = mutate_bullets,
    error_call = error_call
  ),
  warning = dplyr_warning_handler(
    state = warnings_state,
    mask = mask,
    error_call = error_call
  )
)
```

**解説:** エラー発生時に、どの式でエラーが発生したかの情報を付加してユーザーに提示します。

#### パターン4: .Callによるネイティブコード呼び出し

**目的:** 高速化が必要な処理をC++で実行

**実装例:**
```r
// ファイル: R/data-mask.R:61-68
private$chops <- .Call(
  dplyr_lazy_vec_chop_impl,
  data,
  rows,
  private$env_current_group_info,
  private$grouped,
  private$rowwise
)
```

**解説:** `.Call()`でC++関数を呼び出し、Rオブジェクトを直接操作します。

---

## 8. 業務フロー追跡の実践例

> このセクションでは、実際の業務フローをコードで追跡する方法を解説します。

### 8.1 フロー追跡の基本手順

1. エントリーポイントを特定（S3ジェネリック関数）
2. 処理の流れを追跡（UseMethod → メソッド実装）
3. DataMaskでの式評価を確認
4. 最終的な結果の構築を確認

### 8.2 フロー追跡の実例

#### 例1: filter()の処理フロー

**概要:** `filter(df, x > 0)` の実行フローを追跡

**処理フロー:**
```
filter() → filter.data.frame() → filter_impl() → filter_rows() → dplyr_row_slice()
```

**詳細な追跡:**

1. **S3ディスパッチ** (`R/filter.R:216-219`)
   ```r
   filter <- function(.data, ..., .by = NULL, .preserve = FALSE) {
     check_by_typo(...)
     check_not_both_by_and_preserve({{ .by }}, .preserve)
     UseMethod("filter")
   }
   ```

2. **data.frameメソッド** (`R/filter.R:231-239`)
   ```r
   filter.data.frame <- function(.data, ..., .by = NULL, .preserve = FALSE) {
     filter_impl(
       .data = .data, ..., .by = {{ .by }},
       .preserve = .preserve, .verb = "filter"
     )
   }
   ```

3. **実装詳細** (`R/filter.R:252-283`)
   ```r
   filter_impl <- function(.data, ..., .by, .preserve, .verb, ...) {
     dots <- dplyr_quosures(...)
     check_filter(dots, error_call = .error_call)

     by <- compute_by(by = {{ .by }}, data = .data, ...)

     loc <- filter_rows(data = .data, dots = dots, by = by, ...)

     dplyr_row_slice(.data, loc, preserve = .preserve)
   }
   ```

4. **行インデックスの計算** (`R/filter.R:285-311`)
   ```r
   filter_rows <- function(data, dots, by, verb, ...) {
     mask <- DataMask$new(data, by, verb, error_call = error_call)
     dots_expanded <- filter_expand(dots, mask = mask, ...)

     filter_eval(dots = dots, dots_expanded = dots_expanded, ...)
   }
   ```

#### 例2: group_by() + summarise() のフロー

**概要:** `df |> group_by(g) |> summarise(m = mean(x))` の処理

**処理フロー:**
```
group_by() → grouped_df() → summarise.grouped_df() → summarise_cols() → 結果
```

**詳細な追跡:**

1. **group_by** (`R/group-by.R:142-155`)
   ```r
   group_by.data.frame <- function(.data, ..., .add = FALSE, .drop = ...) {
     groups <- group_by_prepare(.data, ..., .add = .add, ...)
     grouped_df(groups$data, groups$group_names, .drop)
   }
   ```

2. **summarise** (`R/summarise.R:140-175`)
   ```r
   summarise.grouped_df <- function(.data, ..., .by = NULL, .groups = NULL) {
     by <- compute_by({{ .by }}, .data, ...)
     cols <- summarise_cols(.data, dplyr_quosures(...), by, "summarise")
     out <- summarise_build(by, cols, "summarise")
     # グループの更新処理...
   }
   ```

### 8.3 フロー追跡チェックリスト

- [ ] エントリーポイント（S3ジェネリック）を特定したか
- [ ] UseMethod()によるディスパッチを確認したか
- [ ] compute_by()でのグループ情報取得を確認したか
- [ ] DataMask作成と式評価を追跡したか
- [ ] エラーハンドリングの仕組みを確認したか
- [ ] 最終的なデータフレーム構築を確認したか

---

## 9. 設計書の参照順序

> このセクションでは、プロジェクト理解のための設計書参照順序を案内します。

### 9.1 目的別ロードマップ

#### 全体像を把握したい場合
1. `README.md` - プロジェクト概要
2. `vignettes/dplyr.Rmd` - 基本的な使い方
3. `DESCRIPTION` - 依存関係の確認
4. `NAMESPACE` - エクスポートされた関数一覧

#### 特定のverbを理解したい場合
1. `R/{verb}.R` - verb本体の実装
2. `tests/testthat/test-{verb}.R` - テストケースから動作理解
3. `man/{verb}.Rd` - ドキュメント
4. `vignettes/` - 関連チュートリアル

#### 改修作業を行う場合
1. 対象機能のソースファイル
2. `R/data-mask.R` - DataMaskの理解
3. 関連するC++ファイル（`src/`）
4. テストファイルで既存動作を確認

### 9.2 ドキュメント一覧

| ドキュメント | 概要 | 参照タイミング |
|-------------|------|---------------|
| `README.md` | プロジェクト概要 | 初回参照 |
| `vignettes/dplyr.Rmd` | 基本チュートリアル | 使い方理解時 |
| `vignettes/programming.Rmd` | tidyevalプログラミング | 内部実装理解時 |
| `vignettes/colwise.Rmd` | across()の使い方 | 列方向操作理解時 |
| `vignettes/two-table.Rmd` | join操作 | 結合処理理解時 |
| `NEWS.md` | 変更履歴 | バージョン差異確認時 |

---

## 10. トラブルシューティング

> このセクションでは、コードリーディング時によくある問題と解決法を解説します。

### よくある疑問と回答

#### Q: `{{ }}` や `!!` は何を意味しますか?
A: tidyevalの演算子です。`{{ }}`は「embrace」と呼ばれ、関数引数を引用/引用解除します。`!!`は「bang-bang」と呼ばれ、引用を解除します。詳細は`vignettes/programming.Rmd`を参照してください。

#### Q: `.Call()`で呼ばれる関数はどこにありますか?
A: `src/`ディレクトリのC++ファイルにあります。関数名からファイルを特定できます（例: `dplyr_mask_eval_all_mutate` → `src/mutate.cpp`）。

#### Q: `private`変数はどこで定義されていますか?
A: R6クラスの`private`リストで定義されています。`R/data-mask.R`の`private = list(...)`セクションを参照してください。

#### Q: テストの実行方法は?
A: プロジェクトルートで `devtools::test()` または特定のファイルに対して `testthat::test_file("tests/testthat/test-mutate.R")` を実行します。

### デバッグのヒント

1. **browser()の挿入**: 関数内に`browser()`を挿入してステップ実行
2. **trace()の使用**: `trace(filter.data.frame, browser)` でブレークポイント設定
3. **rlang::last_trace()**: エラー発生時のスタックトレース確認
4. **options(error = recover)**: エラー時に対話的デバッグモードに入る

---

## 付録

### A. 用語集

| 用語 | 説明 |
|-----|------|
| verb | dplyrの主要操作関数（mutate, filter, select等） |
| tibble | 拡張データフレーム |
| quosure | 式と環境のペア（遅延評価） |
| data masking | データフレームの列を直接参照可能にする仕組み |
| grouped_df | グループ化されたデータフレーム |
| rowwise_df | 行単位操作用データフレーム |
| tidyselect | 列選択のためのDSL |
| NSE | Non-Standard Evaluation（非標準評価） |
| vctrs | ベクトル操作の基盤パッケージ |
| rlang | tidyevalを提供するパッケージ |

### B. ファイル一覧

| ファイル/ディレクトリ | 説明 | 主な内容 |
|---------------------|------|---------|
| `R/mutate.R` | mutate verb | 列の追加・変更 |
| `R/filter.R` | filter verb | 行のフィルタリング |
| `R/select.R` | select verb | 列の選択 |
| `R/arrange.R` | arrange verb | 行のソート |
| `R/summarise.R` | summarise verb | グループ集計 |
| `R/group-by.R` | group_by verb | グループ化 |
| `R/grouped-df.R` | grouped_dfクラス | グループ化データフレーム |
| `R/data-mask.R` | DataMaskクラス | 式評価エンジン |
| `R/join.R` | join関数群 | テーブル結合 |
| `R/across.R` | across関数 | 複数列への関数適用 |
| `R/context.R` | コンテキスト関数 | cur_group(), n()等 |
| `src/dplyr.h` | C++ヘッダー | 共通定義 |

### C. 参考資料

- [dplyr公式ドキュメント](https://dplyr.tidyverse.org/)
- [R for Data Science](https://r4ds.hadley.nz/)
- [Advanced R (2nd Edition)](https://adv-r.hadley.nz/)
- [rlang Tidy Evaluation](https://rlang.r-lib.org/reference/topic-defuse.html)
- [R6 Classes](https://r6.r-lib.org/)
- [Writing R Extensions](https://cran.r-project.org/doc/manuals/r-release/R-exts.html)
