{"cells":[{"metadata":{},"cell_type":"markdown","source":"It is easy and fast (less than a minute for full data) to calculate all distances between atoms using vectorized code and data.table."},{"metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"cell_type":"code","source":"require(data.table)\ndstruct = fread('../input/structures.csv')\n","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Let's build a single vector with all the molecule-atom couples with an identifier, a coordinate matrix and a vector with the atom types"},{"metadata":{"_cell_guid":"79c7e3d0-c299-4dcb-8224-4455121ee9b0","_uuid":"d629ff2d2480ee46fbb7e2d37f6b5fab8052498a","trusted":true},"cell_type":"code","source":"dstruct[,i:=.I]\nlist_atoms = dstruct[,.(molecule_name,atom_index,i)]\nmd = as.matrix(dstruct[,.(x,y,z)])\natom_type =unlist(dstruct[,atom])","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Then  we can build the list of all atoms couples for all molecules in structures.csv"},{"metadata":{"trusted":true},"cell_type":"code","source":"system.time(\n    {\n     aij<-merge(list_atoms,list_atoms,by='molecule_name',allow.cartesian=TRUE)\n     aij[,atom_index.y:=NULL]\n     colnames(aij)<-c('molecule_name','atom_index','i','j')\n     aij<-aij[i!=j]\n     aij[,atj:=atom_type[j]]\n    }\n)\ndim(aij)","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"And finally all the distances between atoms"},{"metadata":{"trusted":true},"cell_type":"code","source":"rs = md[aij[,i],]-md[aij[,j],]\nsystem.time(aij[,d:=sqrt(rowSums(rs*rs))])\nhead(aij)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"From this information we can build a descriptor using the distances to the k nearest neighbors"},{"metadata":{"trusted":true},"cell_type":"code","source":"k=5\ngroup=c('molecule_name','atom_index')\naij_knn=copy(aij)\nsetkeyv(aij_knn,c('molecule_name','atom_index','d'))\nsystem.time(or<-aij_knn[, .(or=seq_len(.N)),by= c('molecule_name','atom_index')]$or)\naij_knn=aij_knn[,or:=or][or<=k]","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"system.time(daij2_knn<-dcast(aij_knn,molecule_name+atom_index~atj+or,value.var=c('d')))\ndaij2_knn[is.na(daij2_knn)]=0\nhead(daij2_knn)","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Instead of select k neighbors for each atom, it can be more 'physically inspired' to calculate the sum of the inverse of the distances to all atoms (Coulomb Potential), inverse of negative exponential (Yukawa) or other distance dependencies"},{"metadata":{"trusted":true},"cell_type":"code","source":"system.time(daij<-aij[,.(coulomb=sum(1/d),yukawa=sum(exp(-d))),by=.(molecule_name,atom_index,atj)])\nsystem.time(daij2<-dcast(daij,molecule_name+atom_index~atj,value.var=c('coulomb','yukawa')))\ndaij2[is.na(daij2)]=0","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"Now we can built the coulomb interactions for all rows in the train+test dataset"},{"metadata":{"trusted":true},"cell_type":"code","source":"train = fread('../input/train.csv')\ntest = fread('../input/test.csv')\nscalar_coupling = train$scalar_coupling_constant\niclass = train$type\nvars=c('molecule_name','atom_index_0','atom_index_1')\n\ndata=rbind(train[,vars,with=F],test[,vars,with=F])\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"data2=merge(data,daij2,by.x=c('molecule_name','atom_index_0'),by.y=c('molecule_name','atom_index'),sort=F)\ndata2=merge(data2,daij2,by.x=c('molecule_name','atom_index_1'),by.y=c('molecule_name','atom_index'),sort=F)\n\nhead(data2)","execution_count":null,"outputs":[]}],"metadata":{"kernelspec":{"display_name":"R","language":"R","name":"ir"},"language_info":{"mimetype":"text/x-r-source","name":"R","pygments_lexer":"r","version":"3.4.2","file_extension":".r","codemirror_mode":"r"}},"nbformat":4,"nbformat_minor":1}