Skip to content

Commit fcb738c

Browse files
Merge pull request #1664 from Kotlin/string-api-docs
Add String API page, update access API overview and EP API
2 parents 84f7a51 + d406935 commit fcb738c

8 files changed

Lines changed: 669 additions & 46 deletions

File tree

docs/StardustDocs/d.tree

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,9 @@
2626
<toc-element topic="Modules.md"/>
2727
</toc-element>
2828
<toc-element topic="concepts.md" accepts-web-file-names="overview.html">
29-
<toc-element topic="apiLevels.md"/>
29+
<toc-element topic="apiLevels.md">
30+
<toc-element topic="StringApi.md"/>
31+
</toc-element>
3032
<toc-element topic="types.md">
3133
<toc-element topic="DataFrame.md"/>
3234
<toc-element topic="DataColumn.md"/>
16.6 KB
Loading
Lines changed: 257 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,257 @@
1+
# String API
2+
3+
<web-summary>
4+
Work with columns in Kotlin DataFrame using simple string-based selectors.
5+
</web-summary>
6+
7+
<card-summary>
8+
Use the String API in Kotlin DataFrame to select columns directly by name and build expressions with minimal setup.
9+
</card-summary>
10+
11+
<link-summary>
12+
An introduction to the Kotlin DataFrame String API for column selection.
13+
</link-summary>
14+
15+
<!---IMPORT org.jetbrains.kotlinx.dataframe.samples.concepts.StringApi-->
16+
17+
The String API is the most basic and straightforward way to select columns
18+
in Kotlin DataFrame [operations](operations.md).
19+
20+
In String API operation overloads, selected column names are provided directly as `String` values
21+
in function arguments:
22+
23+
<!---FUN simpleSelect-->
24+
25+
```kotlin
26+
// Select "name" and "info" columns
27+
df.select("name", "info")
28+
```
29+
30+
<!---END-->
31+
32+
## String Column Accessors
33+
34+
The String API can also be used inside the
35+
[Columns Selection DSL](ColumnSelectors.md) and
36+
[row expressions](DataRow.md#row-expressions)
37+
via *`String` column accessors*.
38+
39+
`String` column accessors allow you to access nested columns and combine them with
40+
[the extensions properties](extensionPropertiesApi.md)
41+
or with any other [CS DSL methods](ColumnSelectors.md#functions-overview).
42+
43+
String column accessors are created using special functions.
44+
In the Columns Selection DSL, they have the special type `ColumnAccessor`,
45+
while in row expressions they resolve to concrete value types.
46+
47+
You can optionally specify the column type as a type argument of the
48+
`String` column accessor creation function.
49+
This is required for row expressions and for some operations with a column selection.
50+
If the specified type does not match the actual column type,
51+
a runtime exception may be thrown.
52+
53+
| Columns Seletcion DSL | Row Expressions | |
54+
|--------------------------------------------|--------------------------|--------------------------------------------------------------------------------------------------------------------------------------------|
55+
| `col("name")` / `col<T>("name")` | `getValue<T>("name")` | Resolves into general [`DataColumn`](DataColumn.md) / row value with the provided `"name"` and type `T`. |
56+
| `colGroup("name")` / `colGroup<T>("name")` | `getColumnGroup("name")` | Resolves into [`ColumnGroup`](DataColumn.md#columngroup) with the provided `"name"` and type `T`. Can be used for accessing nested columns |
57+
| `valueCol("name")` / `valueCol<T>("name")` | `getValue<T>("name")` | Resolves into [`ValueColumn`](DataColumn.md#valuecolumn) / row value with the provided `"name"` and type `T`. |
58+
| `frameCol("name")` / `frameCol<T>("name")` | `getFrameColumn("name")` | Resolves into [`FrameColumn`](DataColumn.md#framecolumn) / `DataFrame` with the provided `"name"` and type `T`. |
59+
60+
> Row Expressions methods may be changed in the future.
61+
> {style = "warning"}
62+
63+
### Example
64+
65+
Consider a simple hierarchical dataframe from
66+
<resource src="example.csv"></resource>.
67+
68+
This table consists of two columns: `name`, which is a `String` column, and `info`,
69+
which is a [**column group**](DataColumn.md#columngroup) containing two nested
70+
[value columns](DataColumn.md#valuecolumn)
71+
`age` of type `Int`, and `height` of type `Double`.
72+
73+
<table width="705">
74+
<thead>
75+
<tr>
76+
<th>name</th>
77+
<th colspan="2">info</th>
78+
</tr>
79+
<tr>
80+
<th></th>
81+
<th>age</th>
82+
<th>height</th>
83+
</tr>
84+
</thead>
85+
<tbody>
86+
<tr>
87+
<td>Alice</td>
88+
<td>23</td>
89+
<td>175.5</td>
90+
</tr>
91+
<tr>
92+
<td>Bob</td>
93+
<td>27</td>
94+
<td>160.2</td>
95+
</tr>
96+
</tbody>
97+
</table>
98+
99+
#### Columns Selection DSL
100+
101+
Get a single "height" subcolumn from the "info" column group
102+
103+
<!---FUN getColumn-->
104+
105+
```kotlin
106+
df.getColumn { colGroup("info").col("height") }
107+
```
108+
109+
<!---END-->
110+
111+
Select the "age" subcolumn from the "info" column group and the "name" column
112+
113+
<!---FUN selectSubcolumnAndColumn-->
114+
115+
```kotlin
116+
df.select { colGroup("info").col("age") and col("name") }
117+
```
118+
119+
<!---END-->
120+
121+
Calculate the mean value of the ("info"/"age") column; specify the column type as a `col` type argument
122+
123+
<!---FUN meanValueBySubcolumn-->
124+
125+
```kotlin
126+
df.mean { colGroup("info").col<Int>("age") }
127+
```
128+
129+
<!---END-->
130+
131+
Combine Extensions Properties and String Column Accessors.
132+
Select "height" and "name" columns, assuming we have extensions properties
133+
for "info" and "name" columns but not for the ("info"->"height") column
134+
135+
<!---FUN combineExtensionsAndStrings-->
136+
137+
```kotlin
138+
df.select { "info".col("height") and name }
139+
```
140+
141+
<!---END-->
142+
143+
Combine Columns Selection DSL and String Column Accessors.
144+
Remove all `Number` columns from the dataframe except ("info"->"age")
145+
146+
<!---FUN removeWithExcept-->
147+
148+
```kotlin
149+
df.remove {
150+
colsAtAnyDepth().colsOf<Number>() except
151+
colGroup("info").col("age")
152+
}
153+
```
154+
155+
<!---END-->
156+
157+
Select all subcolumns from the "info" column group
158+
159+
<!---FUN selectSubcolumns-->
160+
161+
```kotlin
162+
df.select { colGroup("info").select { col("age") and col("height") } }
163+
// or
164+
df.select { colGroup("info").allCols() }
165+
```
166+
167+
<!---END-->
168+
169+
170+
#### Row Expressions
171+
172+
Add a new "heightInt" column by casting the "height" column values to `Int`
173+
174+
<!---FUN addColumnFromSubcolumn-->
175+
176+
```kotlin
177+
df.add("heightInt") {
178+
"info"["height"]<Double>().toInt()
179+
}
180+
```
181+
182+
<!---END-->
183+
184+
Filter rows where the ("info"->"age") column value is greater than or equal to 18
185+
186+
<!---FUN filterBySubcolumn-->
187+
188+
```kotlin
189+
df.filter { "info"["age"]<Int>() >= 18 }
190+
```
191+
192+
<!---END-->
193+
194+
195+
### Invoked String API
196+
197+
> This API is outdated and may be changed in the future.
198+
>
199+
> Please don't mix it with the `col`/`colGroup` methods.
200+
>
201+
> We don't recommend using it in production code.
202+
> {style = "warning"}
203+
204+
Alternatively, you can use the `String` invocation (optional typed argument) for column accessor creation.
205+
It will create the same column accessors as in the Columns Selection DSL.
206+
You can access nested columns using the
207+
`String.get` or `String.invoke` operators or using the ` String.select {} ` function,
208+
where the receiver is the column group name.
209+
210+
<!---FUN invocatedStringsApi-->
211+
212+
```kotlin
213+
// Columns Selection DSL
214+
215+
// Get a single "height" subcolumn from the "info" column group
216+
df.getColumn { "info"["height"]<Double>() }
217+
218+
// Select the "age" subcolumn of the "info" column group
219+
// and the "name" column
220+
df.select { "info"["age"] and "name"() }
221+
222+
// Calculate the mean value of the ("info"->"age") column;
223+
// specify the column type as an invocation type argument
224+
df.mean { "info" { "age"<Int>() } }
225+
226+
// Select all subcolumns from the "info" column group
227+
df.select { "info" { "age"() and "height"() } }
228+
// or
229+
df.select { "info".allCols() }
230+
231+
// Row Expressions
232+
233+
// Add a new "heightInt" column by
234+
// casting the "height" column values to `Int`
235+
df.add("heightInt") {
236+
"info"["height"]<Double>().toInt()
237+
}
238+
239+
// Filter rows where the ("info"->"age") column value
240+
// is greater than or equal to 18
241+
df.filter { "info"["age"]<Int>() >= 18 }
242+
```
243+
244+
<!---END-->
245+
246+
## When should I use the String API?
247+
248+
The String API is a good starting point for learning the library
249+
and understanding how column selection works.
250+
251+
For production code we strongly recommend using the
252+
[**Extension Properties API**](extensionPropertiesApi.md) instead.
253+
It is more concise, fully type-safe, and provides better IDE support.
254+
255+
However, note that sometimes the usage of Extension Properties API is not possible
256+
or may require too many excess actions.
257+
In such cases, use [](#string-column-accessors).

0 commit comments

Comments
 (0)