Repository: mars-project/mars

Issue:
[BUG] Setitem for DataFrame leads to a wrong dtypes
<!--
Thank you for your contribution!

Please review https://github.com/mars-project/mars/blob/master/CONTRIBUTING.rst before opening an issue.
-->

**Describe the bug**
Add columns for a DataFrame will lead to a wrong dtypes of input DataFrame.

**To Reproduce**
```python
In [1]: import mars.dataframe as md                                                                 

In [2]: a = md.DataFrame({'a':[1,2,3]})                                                             

In [3]: a['new'] = 1                                                                                

In [4]: a.op.inputs                                                                                 
Out[4]: [DataFrame <op=DataFrameDataSource, key=c212164d24d96ed634711c3b97f334cb>]

In [5]: a.op.inputs[0].dtypes                                                                       
Out[5]: 
a      int64
new    int64
dtype: object
```
**Expected behavior**
Input DataFrame's dtypes should have only one column.



Discussion:
Reopen as chunk's dtypes is still wrong:

``` Python
In [1]: import pandas as pd                                                                                      

In [2]: import mars.dataframe as md                                                                              

In [3]: a = md.DataFrame({'a':[1,2,3]})                                                                          

In [4]: a['new'] = 1                                                                                             

In [5]: tiled = a.tiles()                                                                                        

In [6]: tiled.chunks[0].inputs[0].dtypes                                                                         
Out[6]: 
a      int64
new    int64
dtype: object


```

Resolving patch:
diff --git a/mars/dataframe/indexing/setitem.py b/mars/dataframe/indexing/setitem.py
--- a/mars/dataframe/indexing/setitem.py
+++ b/mars/dataframe/indexing/setitem.py
@@ -128,7 +128,7 @@ def tile(cls, op):
                         value_chunk = value.cix[c.index[0], ]
                         chunk_inputs = [c, value_chunk]
 
-                    dtypes = c.dtypes
+                    dtypes = c.dtypes.copy(deep=True)
                     dtypes.loc[out.dtypes.index[-1]] = out.dtypes.iloc[-1]
                     chunk = chunk_op.new_chunk(chunk_inputs,
                                                shape=(c.shape[0], c.shape[1] + 1),


Test patch:
diff --git a/mars/dataframe/indexing/tests/test_indexing.py b/mars/dataframe/indexing/tests/test_indexing.py
--- a/mars/dataframe/indexing/tests/test_indexing.py
+++ b/mars/dataframe/indexing/tests/test_indexing.py
@@ -650,6 +650,9 @@ def testSetitem(self):
         self.assertEqual(tiled.chunks[2].shape, (2, 3))
         pd.testing.assert_series_equal(tiled.inputs[0].dtypes, data.dtypes)
 
+        for c in tiled.chunks:
+            pd.testing.assert_series_equal(c.inputs[0].dtypes, data.dtypes)
+
     def testResetIndex(self):
         data = pd.DataFrame([('bird',    389.0),
                              ('bird',     24.0),