diff --git a/README.md b/README.md index 8a20fb0..2886730 100644 --- a/README.md +++ b/README.md @@ -50,7 +50,7 @@ Note: GPU is not required to run this custom module. 5. Start ComfyUI. ### Troubleshooting for installation -This custom node module requires pandas and matplotlib, which are not included in the default ComfyUI installation. If you install this module using ComfyUI Manager, these packages should be installed automatically. However, if the installation fails, refer to the pandas and matplotlib documentation for manual installation. +This custom node module requires pandas and matplotlib, which are not included in the default ComfyUI installation. If you install this module using ComfyUI Manager, these packages should be installed automatically. However, if installation fails, refer to the pandas and matplotlib documentation for manual installation. ## How to Use Refer to [User's Guide](docs/ug.md) \ No newline at end of file diff --git a/docs/images/inner_join.png b/docs/images/inner_join.png new file mode 100644 index 0000000..e5b41b9 Binary files /dev/null and b/docs/images/inner_join.png differ diff --git a/docs/images/join_data_load.png b/docs/images/join_data_load.png new file mode 100644 index 0000000..56feba5 Binary files /dev/null and b/docs/images/join_data_load.png differ diff --git a/docs/images/left_join.png b/docs/images/left_join.png new file mode 100644 index 0000000..120a4a4 Binary files /dev/null and b/docs/images/left_join.png differ diff --git a/docs/images/outer_join.png b/docs/images/outer_join.png new file mode 100644 index 0000000..14c4b16 Binary files /dev/null and b/docs/images/outer_join.png differ diff --git a/docs/images/right_join.png b/docs/images/right_join.png new file mode 100644 index 0000000..4034575 Binary files /dev/null and b/docs/images/right_join.png differ diff --git a/docs/ug.md b/docs/ug.md index de14aaa..77f4a59 100644 --- a/docs/ug.md +++ b/docs/ug.md @@ -40,8 +40,29 @@ Use **Pandas Select Columns** for selecting columns, **Pandas Select Rows** to s ![Pandas select subset](images/subset.jpg) -## Joining DataFrames. +## Joining DataFrames Use **Pandas Join**. You can select from inner, left, right, outer joins. +First, use two **Pandas Load CSV** nodes to load two CSVs for the left DataFrame and right DataFrame. + +![Load two CSVs into DataFrames](images/join_data_load.png) + +### Inner join +Specify the common column in the "on column name" field, and set the join method to **inner** in the **Pandas Join** node. +![Inner join](images/inner_join.png) + +### Left join +Specify the common column in the "on column name" field, and set the join method to **left** in the **Pandas Join** node. +![Left join](images/left_join.png) + +### Right join +Specify the common column in the "on column name" field, and set the join method to **right** in the **Pandas Join** node. +![Right join](images/right_join.png) + +### Outer join +Specify the common column in the "on column name" field, and set the join method to **outer** in the **Pandas Join** node. +![Outer join](images/outer_join.png) + +The workflow file examples/workflows/join.json contains all of the above cases. ## Extract the first few rows Use **Pandas Head**. @@ -62,6 +83,8 @@ Use **Pandas To String**. This node is to convert the DataFrame to a displayable ## Displaying charts or plots Use one of the below: +| Node | Purpose | +|---|---| | **MPL Bar Chart** | Generate a bar chart | | **MPL Line Plot** | Generate a line plot | | **MPL Scatter Plot** | Generate a scatter plot | diff --git a/examples/datasets/actor.csv b/examples/datasets/actor.csv new file mode 100644 index 0000000..0db3b1e --- /dev/null +++ b/examples/datasets/actor.csv @@ -0,0 +1,21 @@ +Name,ActorID +Barron Sawyer, 1 +Elara Whitmore, 2 +Jaxon Vance, 3 +Seraphina Lowell, 4 +Dorian Kessler, 5 +Valeria Knox, 6 +Orin Mercer, 7 +Celeste Draven, 8 +Lucian Hartwell, 9 +Marisol Quinn, 10 +Felix Holloway, 11 +Rowan Sinclair, 12 +Sienna Wren, 13 +Cassius Vale, 14 +Livia Monroe, 15 +Gideon Thorne, 16 +Zara Fontaine, 17 +Maverick Calloway, 18 +Isolde Mercer, 19 +Ronan Delacroix, 20 diff --git a/examples/datasets/movie.csv b/examples/datasets/movie.csv new file mode 100644 index 0000000..e3bd299 --- /dev/null +++ b/examples/datasets/movie.csv @@ -0,0 +1,21 @@ +Title,MovieID,ActorID +Shadow Circuit, 1, 5 +The Last Ember, 2, 4 +Echoes of Orion, 3, 3 +Neon Revenant, 4, 2 +Fractured Horizon, 5, 1 +Blood and Chrome, 6, 10 +The Silent Epoch, 7, 9 +Ashes of Tomorrow, 8, 8 +Hyperion’s Wake, 9, 7 +Obsidian Mirage, 10, 6 +The Hollow Accord, 11, 5 +Lunar Divide, 12, 3 +Redshift Paradox, 13, 1 +Phantom Genesis, 14, 4 +Vanishing Point Protocol, 15, 2 +Nocturne Zero, 16, +Polaris Run, 17, +The Gilded Warden, 18, +Aetherfall, 19, +Terminal Sanctum, 20, diff --git a/examples/workflows/join.json b/examples/workflows/join.json new file mode 100644 index 0000000..e034a35 --- /dev/null +++ b/examples/workflows/join.json @@ -0,0 +1 @@ +{"last_node_id":34,"last_link_id":30,"nodes":[{"id":24,"type":"MarkdownNote","pos":[824.4011840820312,3057.402587890625],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":0,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Left join"],"color":"#432","bgcolor":"#653"},{"id":34,"type":"MarkdownNote","pos":[830.350341796875,4215.66162109375],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":1,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Outer join"],"color":"#432","bgcolor":"#653"},{"id":27,"type":"PandasJoin","pos":[817.4930419921875,3736.85791015625],"size":[400,200],"flags":{},"order":12,"mode":0,"inputs":[{"name":"left_dataframe_json","type":"STRING","link":27,"widget":{"name":"left_dataframe_json"}},{"name":"right_dataframe_json","type":"STRING","link":28,"widget":{"name":"right_dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[23],"slot_index":0}],"properties":{"Node name for S&R":"PandasJoin"},"widgets_values":["","","ActorID","right"]},{"id":1,"type":"PandasLoadCSV","pos":[-607.8720092773438,2361.45849609375],"size":[410.5992736816406,95.68482208251953],"flags":{},"order":5,"mode":0,"inputs":[],"outputs":[{"name":"STRING","type":"STRING","links":[13,20,25,27,30],"slot_index":0}],"properties":{"Node name for S&R":"PandasLoadCSV"},"widgets_values":["custom_nodes/data-analysis/examples/datasets/movie.csv"]},{"id":13,"type":"PandasLoadCSV","pos":[-608.0108032226562,2733.447265625],"size":[410.5992736816406,95.68482208251953],"flags":{},"order":7,"mode":0,"inputs":[],"outputs":[{"name":"STRING","type":"STRING","links":[14,21,26,28,29],"slot_index":0}],"properties":{"Node name for S&R":"PandasLoadCSV"},"widgets_values":["custom_nodes/data-analysis/examples/datasets/actor.csv"]},{"id":10,"type":"PandasShowDataFrame","pos":[-66.52587890625,2354.16455078125],"size":[427.6637878417969,314.1942443847656],"flags":{},"order":8,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":13,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[],"slot_index":0,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Title MovieID ActorID\n0 Shadow Circuit 1 5.0\n1 The Last Ember 2 4.0\n2 Echoes of Orion 3 3.0\n3 Neon Revenant 4 2.0\n4 Fractured Horizon 5 1.0\n5 Blood and Chrome 6 10.0\n6 The Silent Epoch 7 9.0\n7 Ashes of Tomorrow 8 8.0\n8 Hyperion’s Wake 9 7.0\n9 Obsidian Mirage 10 6.0\n10 The Hollow Accord 11 5.0\n11 Lunar Divide 12 3.0\n12 Redshift Paradox 13 1.0\n13 Phantom Genesis 14 4.0\n14 Vanishing Point Protocol 15 2.0\n15 Nocturne Zero 16 NaN\n16 Polaris Run 17 NaN\n17 The Gilded Warden 18 NaN\n18 Aetherfall 19 NaN\n19 Terminal Sanctum 20 NaN"]},{"id":14,"type":"PandasShowDataFrame","pos":[-64.7003173828125,2732.39013671875],"size":[427.6637878417969,314.1942443847656],"flags":{},"order":9,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":14,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[],"slot_index":0,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Name ActorID\n0 Barron Sawyer 1\n1 Elara Whitmore 2\n2 Jaxon Vance 3\n3 Seraphina Lowell 4\n4 Dorian Kessler 5\n5 Valeria Knox 6\n6 Orin Mercer 7\n7 Celeste Draven 8\n8 Lucian Hartwell 9\n9 Marisol Quinn 10\n10 Felix Holloway 11\n11 Rowan Sinclair 12\n12 Sienna Wren 13\n13 Cassius Vale 14\n14 Livia Monroe 15\n15 Gideon Thorne 16\n16 Zara Fontaine 17\n17 Maverick Calloway 18\n18 Isolde Mercer 19\n19 Ronan Delacroix 20"]},{"id":16,"type":"PandasJoin","pos":[828.50830078125,2583.21875],"size":[400,200],"flags":{},"order":10,"mode":0,"inputs":[{"name":"left_dataframe_json","type":"STRING","link":20,"widget":{"name":"left_dataframe_json"}},{"name":"right_dataframe_json","type":"STRING","link":21,"widget":{"name":"right_dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[19],"slot_index":0}],"properties":{"Node name for S&R":"PandasJoin"},"widgets_values":["","","ActorID","inner"]},{"id":22,"type":"PandasJoin","pos":[824.6515502929688,3171.81298828125],"size":[400,200],"flags":{},"order":11,"mode":0,"inputs":[{"name":"left_dataframe_json","type":"STRING","link":25,"widget":{"name":"left_dataframe_json"}},{"name":"right_dataframe_json","type":"STRING","link":26,"widget":{"name":"right_dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[22],"slot_index":0}],"properties":{"Node name for S&R":"PandasJoin"},"widgets_values":["","","ActorID","left"]},{"id":23,"type":"PandasShowDataFrame","pos":[1298.7039794921875,3169.053466796875],"size":[437.3924865722656,328.610595703125],"flags":{},"order":15,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":22,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":null,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Title MovieID ActorID Name\n0 Shadow Circuit 1 5.0 Dorian Kessler\n1 The Last Ember 2 4.0 Seraphina Lowell\n2 Echoes of Orion 3 3.0 Jaxon Vance\n3 Neon Revenant 4 2.0 Elara Whitmore\n4 Fractured Horizon 5 1.0 Barron Sawyer\n5 Blood and Chrome 6 10.0 Marisol Quinn\n6 The Silent Epoch 7 9.0 Lucian Hartwell\n7 Ashes of Tomorrow 8 8.0 Celeste Draven\n8 Hyperion’s Wake 9 7.0 Orin Mercer\n9 Obsidian Mirage 10 6.0 Valeria Knox\n10 The Hollow Accord 11 5.0 Dorian Kessler\n11 Lunar Divide 12 3.0 Jaxon Vance\n12 Redshift Paradox 13 1.0 Barron Sawyer\n13 Phantom Genesis 14 4.0 Seraphina Lowell\n14 Vanishing Point Protocol 15 2.0 Elara Whitmore\n15 Nocturne Zero 16 NaN None\n16 Polaris Run 17 NaN None\n17 The Gilded Warden 18 NaN None\n18 Aetherfall 19 NaN None\n19 Terminal Sanctum 20 NaN None"]},{"id":28,"type":"PandasShowDataFrame","pos":[1302.0699462890625,3739.05859375],"size":[443.3382263183594,375.1855773925781],"flags":{},"order":16,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":23,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":null,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Title MovieID ActorID Name\n0 Fractured Horizon 5.0 1 Barron Sawyer\n1 Redshift Paradox 13.0 1 Barron Sawyer\n2 Neon Revenant 4.0 2 Elara Whitmore\n3 Vanishing Point Protocol 15.0 2 Elara Whitmore\n4 Echoes of Orion 3.0 3 Jaxon Vance\n5 Lunar Divide 12.0 3 Jaxon Vance\n6 The Last Ember 2.0 4 Seraphina Lowell\n7 Phantom Genesis 14.0 4 Seraphina Lowell\n8 Shadow Circuit 1.0 5 Dorian Kessler\n9 The Hollow Accord 11.0 5 Dorian Kessler\n10 Obsidian Mirage 10.0 6 Valeria Knox\n11 Hyperion’s Wake 9.0 7 Orin Mercer\n12 Ashes of Tomorrow 8.0 8 Celeste Draven\n13 The Silent Epoch 7.0 9 Lucian Hartwell\n14 Blood and Chrome 6.0 10 Marisol Quinn\n15 None NaN 11 Felix Holloway\n16 None NaN 12 Rowan Sinclair\n17 None NaN 13 Sienna Wren\n18 None NaN 14 Cassius Vale\n19 None NaN 15 Livia Monroe\n20 None NaN 16 Gideon Thorne\n21 None NaN 17 Zara Fontaine\n22 None NaN 18 Maverick Calloway\n23 None NaN 19 Isolde Mercer\n24 None NaN 20 Ronan Delacroix"]},{"id":29,"type":"MarkdownNote","pos":[814.576416015625,3617.432373046875],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":2,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Right join"],"color":"#432","bgcolor":"#653"},{"id":32,"type":"PandasJoin","pos":[833.5746459960938,4331.5478515625],"size":[400,200],"flags":{},"order":13,"mode":0,"inputs":[{"name":"left_dataframe_json","type":"STRING","link":30,"widget":{"name":"left_dataframe_json"}},{"name":"right_dataframe_json","type":"STRING","link":29,"widget":{"name":"right_dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":[24],"slot_index":0}],"properties":{"Node name for S&R":"PandasJoin"},"widgets_values":["","","ActorID","outer"]},{"id":33,"type":"PandasShowDataFrame","pos":[1309.1181640625,4335.92041015625],"size":[465.1393127441406,435.6340026855469],"flags":{},"order":17,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":24,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":null,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Title MovieID ActorID Name\n0 Fractured Horizon 5.0 1.0 Barron Sawyer\n1 Redshift Paradox 13.0 1.0 Barron Sawyer\n2 Neon Revenant 4.0 2.0 Elara Whitmore\n3 Vanishing Point Protocol 15.0 2.0 Elara Whitmore\n4 Echoes of Orion 3.0 3.0 Jaxon Vance\n5 Lunar Divide 12.0 3.0 Jaxon Vance\n6 The Last Ember 2.0 4.0 Seraphina Lowell\n7 Phantom Genesis 14.0 4.0 Seraphina Lowell\n8 Shadow Circuit 1.0 5.0 Dorian Kessler\n9 The Hollow Accord 11.0 5.0 Dorian Kessler\n10 Obsidian Mirage 10.0 6.0 Valeria Knox\n11 Hyperion’s Wake 9.0 7.0 Orin Mercer\n12 Ashes of Tomorrow 8.0 8.0 Celeste Draven\n13 The Silent Epoch 7.0 9.0 Lucian Hartwell\n14 Blood and Chrome 6.0 10.0 Marisol Quinn\n15 None NaN 11.0 Felix Holloway\n16 None NaN 12.0 Rowan Sinclair\n17 None NaN 13.0 Sienna Wren\n18 None NaN 14.0 Cassius Vale\n19 None NaN 15.0 Livia Monroe\n20 None NaN 16.0 Gideon Thorne\n21 None NaN 17.0 Zara Fontaine\n22 None NaN 18.0 Maverick Calloway\n23 None NaN 19.0 Isolde Mercer\n24 None NaN 20.0 Ronan Delacroix\n25 Nocturne Zero 16.0 NaN None\n26 Polaris Run 17.0 NaN None\n27 The Gilded Warden 18.0 NaN None\n28 Aetherfall 19.0 NaN None\n29 Terminal Sanctum 20.0 NaN None"]},{"id":11,"type":"MarkdownNote","pos":[-602.6942138671875,2221.46630859375],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":4,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Load Movie table (LEFT DataFrame)"],"color":"#432","bgcolor":"#653"},{"id":12,"type":"MarkdownNote","pos":[-605.7132568359375,2591.47021484375],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":6,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Load Actor table (RIGHT DataFrame)"],"color":"#432","bgcolor":"#653"},{"id":18,"type":"MarkdownNote","pos":[828.9031982421875,2464.126953125],"size":[405.45428466796875,61.54335021972656],"flags":{},"order":3,"mode":0,"inputs":[],"outputs":[],"properties":{},"widgets_values":["# Inner join"],"color":"#432","bgcolor":"#653"},{"id":17,"type":"PandasShowDataFrame","pos":[1305.4864501953125,2582.239501953125],"size":[451.2658386230469,270.14410400390625],"flags":{},"order":14,"mode":0,"inputs":[{"name":"dataframe_json","type":"STRING","link":19,"widget":{"name":"dataframe_json"}}],"outputs":[{"name":"STRING","type":"STRING","links":null,"shape":6}],"properties":{"Node name for S&R":"PandasShowDataFrame"},"widgets_values":[""," Title MovieID ActorID Name\n0 Shadow Circuit 1 5 Dorian Kessler\n1 The Last Ember 2 4 Seraphina Lowell\n2 Echoes of Orion 3 3 Jaxon Vance\n3 Neon Revenant 4 2 Elara Whitmore\n4 Fractured Horizon 5 1 Barron Sawyer\n5 Blood and Chrome 6 10 Marisol Quinn\n6 The Silent Epoch 7 9 Lucian Hartwell\n7 Ashes of Tomorrow 8 8 Celeste Draven\n8 Hyperion’s Wake 9 7 Orin Mercer\n9 Obsidian Mirage 10 6 Valeria Knox\n10 The Hollow Accord 11 5 Dorian Kessler\n11 Lunar Divide 12 3 Jaxon Vance\n12 Redshift Paradox 13 1 Barron Sawyer\n13 Phantom Genesis 14 4 Seraphina Lowell\n14 Vanishing Point Protocol 15 2 Elara Whitmore"]}],"links":[[13,1,0,10,0,"STRING"],[14,13,0,14,0,"STRING"],[19,16,0,17,0,"STRING"],[20,1,0,16,0,"STRING"],[21,13,0,16,1,"STRING"],[22,22,0,23,0,"STRING"],[23,27,0,28,0,"STRING"],[24,32,0,33,0,"STRING"],[25,1,0,22,0,"STRING"],[26,13,0,22,1,"STRING"],[27,1,0,27,0,"STRING"],[28,13,0,27,1,"STRING"],[29,13,0,32,1,"STRING"],[30,1,0,32,0,"STRING"]],"groups":[],"config":{},"extra":{"ds":{"scale":0.6727499949325617,"offset":[-509.5429991188312,-2376.8493782649657]},"node_versions":{"data-analysis":"3fbe2d3d0d9fcc3d3358eb6cc8ac844d12d56049"},"ue_links":[]},"version":0.4} \ No newline at end of file