fzxz.py 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353
  1. # -*- coding: utf-8 -*-
  2. import os
  3. import sys
  4. import log
  5. import uuid
  6. import appconfig
  7. import arcpy
  8. import datetime
  9. import time
  10. import utils
  11. from arcpy import env
  12. from db.oracle import Oracle
  13. reload(sys)
  14. sys.setdefaultencoding('utf-8')
  15. class Fzxz:
  16. def __init__(self, data):
  17. self.bsm = data
  18. self.db = Oracle(appconfig.DB_CONN)
  19. log.info(data)
  20. self.fxlog(self.bsm, "info", "开始进行选址分析")
  21. # 读任务
  22. self.task()
  23. # 选址GDB
  24. self.root = os.path.dirname(os.path.abspath(__file__))
  25. path = os.path.join(self.root, "out")
  26. self.tbxPath = os.path.abspath(os.path.join(self.root, "../tbxs"))
  27. if not os.path.exists(path):
  28. os.makedirs(path)
  29. self.outGdb = os.path.join(path, "{0}.gdb".format(data))
  30. arcpy.Delete_management(self.outGdb)
  31. arcpy.CreateFileGDB_management(path, "{0}.gdb".format(data))
  32. # 输出文件夹里面已经有内容的,就覆盖掉
  33. env.overwriteOutput = True
  34. # 设置工作空间
  35. env.workspace = appconfig.SDE["KJGH"]
  36. def task(self):
  37. '''加载数据-任务、因子'''
  38. sql = "SELECT a.BSM,a.SJY,a.YDXZ_BSM,a.FWLX,a.XZFW,a.YDMJBEGIN,a.YDMJEND,a.KDDK,a.ZDPD,b.SJYMC,b.DMZD,b.MCZD,b.FZBS,c.MC,b.XZQDMZD,b.XZQMCZD FROM KJGH.T_FZSS_FZXZ a INNER JOIN KJGH.T_FZSS_FZXZ_SJY b ON a.SJY = b.BSM LEFT JOIN KJGH.T_FZSS_FZXZ_DICT c ON b.FZBS = C.FZBS AND a.YDXZ_BSM = c.DM where a.BSM='{0}'".format(
  39. self.bsm)
  40. tasks = self.db.query(sql)
  41. if len(tasks) == 0:
  42. self.fxlog(self.bsm, "error", "任务标识错误[{0}]".format(self.bsm))
  43. raise Exception("任务标识错误[{0}]".format(self.bsm))
  44. self.task = tasks[0]
  45. sql = "SELECT A.BSM,A.RWBSM,A.YZBSM,A.YXYZMC,A.YZTJ,A.YXZ,B.SJLX,B.SJY,B.GLTJ,B.FXJG_C,B.FXJG_N FROM KJGH.T_FZSS_FZXZ_XZYZ A LEFT JOIN KJGH.T_FZSS_FZXZ_YZ B ON A.YZBSM = B.BSM WHERE A.RWBSM = '{0}'".format(
  46. self.bsm)
  47. self.xzyz = self.db.query(sql)
  48. yznames = ""
  49. for yz in self.xzyz:
  50. yznames = yznames + yz['YXYZMC'] + "、"
  51. logs = "选址参数:数据源={0},用地性质={1},用地面积={2}-{3},影响因子={4}"
  52. logs = logs.format(self.task["SJYMC"],
  53. self.task["MC"],
  54. self.task["YDMJBEGIN"],
  55. self.task["YDMJEND"],
  56. yznames[:-1])
  57. self.fxlog(self.bsm, "info", logs)
  58. def run(self):
  59. # 1.范围导入
  60. # 设置工作空间
  61. self.xzfw = r"{0}\XZFW".format(self.outGdb)
  62. # 范围
  63. if self.task["FWLX"] == 0:
  64. arcpy.Select_analysis("SDE.XZQXZ", self.xzfw, "XZQDM = '{0}'".format(self.task["XZFW"]))
  65. arcpy.AddField_management(self.xzfw, "RWBSM", "TEXT")
  66. with arcpy.da.UpdateCursor(self.xzfw, "RWBSM") as cursor:
  67. for row in cursor:
  68. row[0] = self.bsm
  69. cursor.updateRow(row)
  70. else:
  71. where = '"RWBSM"=\'{0}\''.format(self.bsm);
  72. arcpy.Select_analysis("KJGH.T_FZSS_FXRW_GIS", self.xzfw, where)
  73. self.fxlog(self.bsm, "info", "载入选址范围完成")
  74. # 2.相交数据源
  75. # env.workspace = appconfig.getSDE(self.task['SJY'])
  76. env.workspace = appconfig.getSDE("SDE")
  77. self.sjy = r"{0}\SJY".format(self.outGdb)
  78. arcpy.Intersect_analysis([self.task['SJY'], self.xzfw], self.sjy)
  79. arcpy.ImportToolbox(os.path.join(self.tbxPath, "xzydyh.tbx"), "xzydyh")
  80. arcpy.fzxz_xzydyh(self.sjy)
  81. self.fxlog(self.bsm, "info", "相交裁剪数据源" + self.task['SJYMC'])
  82. # 3.条件过滤
  83. if self.task['YDXZ_BSM'] != '' and self.task['YDXZ_BSM'] != None:
  84. where = '"{0}" LIKE \'{1}%\''.format(self.task['DMZD'], self.task['YDXZ_BSM'])
  85. tjgl = r"{0}\TJGL".format(self.outGdb)
  86. arcpy.Select_analysis(self.sjy, tjgl, where)
  87. self.sjy = tjgl
  88. # 4.因子
  89. for yz in self.xzyz:
  90. sjlx = yz['SJLX'].lower()
  91. if sjlx == 'sde':
  92. self.yzfx(yz)
  93. self.fxlog(self.bsm, "info", "{0}因子影响分析完成".format(yz['YXYZMC']))
  94. # elif sjlx == 'geoserver':
  95. # self.geoserver(yz)
  96. # elif sjlx == 'arcgisserver':
  97. # self.arcgisserver(yz)
  98. else:
  99. self.fxlog(self.bsm, "error", "影响因子数据源错误[{0}]".format(yz['YXYZMC']))
  100. raise Exception("影响因子数据源错误[{0}]".format(yz['YXYZMC']))
  101. # 5.面积
  102. log.info("面积")
  103. mjField = "TBMJ"
  104. arcpy.AddField_management(self.sjy, mjField, "DOUBLE")
  105. arcpy.CalculateField_management(self.sjy, mjField, "!shape.area@SQUAREMETERS!", "PYTHON_9.3")
  106. mjWhere = ""
  107. bBegin = self.task['YDMJBEGIN'] != "" and self.task['YDMJBEGIN'] != None
  108. bEnd = self.task['YDMJEND'] != "" and self.task['YDMJEND'] != None
  109. #TODO 面积筛选字段配置 之前版本是MJ现替换成了mjField 计算后的面积
  110. if bBegin and bEnd:
  111. mjWhere = "TBMJ >= {0} and TBMJ <= {1} ".format(self.task['YDMJBEGIN'], self.task['YDMJEND'])
  112. elif bBegin:
  113. mjWhere = "TBMJ >= {0}".format(self.task['YDMJBEGIN'])
  114. elif bEnd:
  115. mjWhere = "TBMJ <= {0}".format(self.task['YDMJEND'])
  116. if mjWhere != "":
  117. out = r"{0}\YZ_MJ".format(self.outGdb)
  118. arcpy.Select_analysis(self.sjy, out, mjWhere)
  119. self.sjy = out
  120. self.fxlog(self.bsm, "info", "用地面积分析完成")
  121. # 6.入结果库
  122. attrs = ["objectid", "objectid_1", "shape", "shape_length", "shape_area", "rwbsm", "tbmj",
  123. self.task['DMZD'].lower(), self.task['MCZD'].lower(), self.task['XZQDMZD'].lower(),
  124. self.task['XZQMCZD'].lower()]
  125. # RWBSM\DLB\DLBM\DLMC\TBMJ\CJSJ\YXFW == rwbsm
  126. fields = arcpy.ListFields(self.sjy)
  127. for field in fields:
  128. if field.name.lower() not in attrs:
  129. arcpy.DeleteField_management(self.sjy, field.name)
  130. # 添加字段
  131. arcpy.AddField_management(self.sjy, "BSM", "TEXT")
  132. arcpy.AddField_management(self.sjy, "TBXL", "SHORT")
  133. arcpy.AddField_management(self.sjy, "DLB", "TEXT")
  134. arcpy.AddField_management(self.sjy, "DLBM", "TEXT")
  135. arcpy.AddField_management(self.sjy, "DLMC", "TEXT")
  136. arcpy.AddField_management(self.sjy, "XZQDM", "TEXT")
  137. arcpy.AddField_management(self.sjy, "XZQMC", "TEXT")
  138. arcpy.AddField_management(self.sjy, "CJSJ", "DATE")
  139. arcpy.AddField_management(self.sjy, "YXFA", "SHORT")
  140. # 结果入库-判读可能没有数据
  141. ufields = ["BSM", "TBXL", "DLB", "DLBM", "DLMC", "XZQDM", "XZQMC", "CJSJ", "YXFA",
  142. self.task['DMZD'].lower(), self.task['MCZD'].lower(), self.task['XZQDMZD'].lower(),
  143. self.task['XZQMCZD'].lower()]
  144. bsmlist = []
  145. tbxl = 0
  146. with arcpy.da.UpdateCursor(self.sjy, ufields, sql_clause=(None, 'ORDER BY TBMJ DESC')) as cursor:
  147. for row in cursor:
  148. tbxl = tbxl + 1
  149. guid = ''.join(str(uuid.uuid1()).split('-'))
  150. bsmlist.append(guid)
  151. row[0] = guid
  152. row[1] = tbxl
  153. row[2] = self.task["SJY"]
  154. row[3] = row[9]
  155. row[4] = row[10]
  156. row[5] = row[11]
  157. row[6] = row[12]
  158. row[7] = datetime.datetime.now()
  159. row[8] = 0
  160. cursor.updateRow(row)
  161. arcpy.Append_management([self.sjy], "KJGH.T_FZSS_FZXZ_JG_GIS", "NO_TEST")
  162. # 7.统计分析
  163. self.tjfx = r"{0}\YZ_TJFX".format(self.outGdb)
  164. tbxl = 0
  165. for bsm in bsmlist:
  166. arcpy.Delete_management(self.tjfx)
  167. arcpy.Select_analysis(self.sjy, self.tjfx, '"BSM"=\'{0}\''.format(bsm))
  168. tbxl = tbxl + 1
  169. for yz in self.xzyz:
  170. sjlx = yz['SJLX'].lower()
  171. if yz['YZTJ'] == 'F':
  172. self.yzjg_FX(bsm, yz)
  173. else:
  174. self.yzjg_TJ(bsm, yz)
  175. self.fxlog(self.bsm, "info", "图斑{0}统计分析完成".format(str(tbxl)))
  176. time.sleep(1)
  177. self.fxlog(self.bsm, "info", "选址完成")
  178. print("####OK####")
  179. def test(self):
  180. self.xzfw = r'E:\99project\P008KJGH\SVN\trunk\SoureCode\2.Api\QM.KJGH.Com\QM.GisPython\fzxz\out\072f6ecbb54a4d5abd68b7ea06421202.gdb\XZFW'
  181. self.sjy = r'E:\99project\P008KJGH\SVN\trunk\SoureCode\2.Api\QM.KJGH.Com\QM.GisPython\fzxz\out\072f6ecbb54a4d5abd68b7ea06421202.gdb\YZ_MJ'
  182. bsmlist = [
  183. "a393c0c004af11ec9e3b4074e0062853",
  184. "a393c0c104af11ecb1f04074e0062853",
  185. "a393e7cf04af11ecadf14074e0062853",
  186. "a393e7d004af11ec9db94074e0062853",
  187. "a393e7d104af11eca8ab4074e0062853",
  188. "a393e7d204af11ec96104074e0062853"
  189. ]
  190. # 统计分析
  191. self.tjfx = r"{0}\YZ_TJFX".format(self.outGdb)
  192. for bsm in bsmlist:
  193. arcpy.Delete_management(self.tjfx)
  194. arcpy.Select_analysis(self.sjy, self.tjfx, '"BSM"=\'{0}\''.format(bsm))
  195. for yz in self.xzyz:
  196. sjlx = yz['SJLX'].lower()
  197. if yz['YZTJ'] == 'F':
  198. self.yzjg_FX(bsm, yz)
  199. else:
  200. self.yzjg_TJ(bsm, yz)
  201. # 4.因子筛选
  202. def yzfx(self, data):
  203. yztj = data['YZTJ'] # 条件
  204. yzsjy = data['SJY'] # 数据
  205. # 条件过滤
  206. if data['GLTJ'] != "" and data['GLTJ'] != None:
  207. out = r"{0}\YZGL_{1}".format(self.outGdb, data['YZBSM'])
  208. arcpy.Select_analysis(yzsjy, out, data['GLTJ'])
  209. yzsjy = out
  210. out = r"{0}\YZ_{1}_{2}".format(self.outGdb, yztj, data['YZBSM'])
  211. xyz = data.get('YXZ')
  212. if yztj == 'C': # 包含
  213. if xyz != '' and xyz != None: # 距离
  214. arcpy.Near_analysis(self.sjy, yzsjy, "{0} Meters".format(xyz), method='GEODESIC')
  215. arcpy.Select_analysis(self.sjy, out, " NEAR_DIST > -1 ")
  216. else:
  217. arcpy.Clip_analysis(self.sjy, yzsjy, out)
  218. self.sjy = out
  219. elif yztj == 'N': # 不包含
  220. if xyz != '' and xyz != None:
  221. arcpy.Near_analysis(self.sjy, yzsjy, "{0} Meters".format(xyz), method='GEODESIC')
  222. arcpy.Select_analysis(self.sjy, out, " NEAR_DIST = -1 ")
  223. else:
  224. clip = r"{0}\YZ_{1}0_{2}".format(self.outGdb, yztj, data['YZBSM'])
  225. arcpy.Clip_analysis(yzsjy, self.xzfw, clip)
  226. arcpy.SymDiff_analysis(self.sjy, clip, out)
  227. self.sjy = out
  228. # 6.因子结果-分析
  229. def yzjg_FX(self, bsm, yz):
  230. '''分析'''
  231. out = r"{0}\YZ_{1}_{2}".format(self.outGdb, yz['YZTJ'], yz['YZBSM'])
  232. arcpy.Clip_analysis(yz["SJY"], self.tjfx, out)
  233. mjField = "TBMJ"
  234. arcpy.AddField_management(out, mjField, "DOUBLE")
  235. arcpy.CalculateField_management(out, mjField, "!shape.area@SQUAREMETERS!", "PYTHON_9.3")
  236. mj = 0;
  237. jgstr = ""
  238. with arcpy.da.SearchCursor(out, ['TBMJ']) as cursor:
  239. for row in cursor:
  240. mj = mj + row[0]
  241. # if mj == 0:
  242. # jgstr = "地块未压占" + yz['YXYZMC']
  243. # else:
  244. # jgstr = round(mj)
  245. self.jgrk(bsm, yz, round(mj))
  246. # 6.因子结果-统计
  247. def yzjg_TJ(self, bsm, yz):
  248. '''统计'''
  249. # self.tjfx
  250. jgstr = yz['FXJG_' + yz['YZTJ']]
  251. keys = utils.regDkh(jgstr)
  252. if len(keys) == 0:
  253. self.jgrk(bsm, yz, jgstr)
  254. else:
  255. self.yztjjl = r"{0}\YZGL_{1}".format(self.outGdb, yz['YZBSM'])
  256. arcpy.Near_analysis(self.yztjjl, self.tjfx, method='GEODESIC')
  257. where = "NEAR_DIST <= {0}".format(yz['YXZ'])
  258. if yz['YZTJ'] == 'N':
  259. where = "NEAR_DIST > {0}".format(yz['YXZ'])
  260. for key in keys:
  261. if key == 'YXZ':
  262. jgstr = jgstr.replace("{YXZ}", yz['YXZ'])
  263. elif key == 'COUNT':
  264. jgstr = jgstr.replace("{COUNT}", self.yzjg_TJ_COUNT(yz, where))
  265. elif key == 'DIST':
  266. jgstr = jgstr.replace("{DIST}", self.yzjg_TJ_DIST(yz, where))
  267. elif key.startswith('YZ.'):
  268. jgstr = jgstr.replace("{" + key + "}", self.yzjg_TJ_YZ(yz, where, key))
  269. elif key.startswith('[') and key.endswith(']'):
  270. jgstr = jgstr.replace("{" + key + "}", self.yzjg_TJ_YZS(yz, where, key))
  271. self.jgrk(bsm, yz, jgstr)
  272. def yzjg_TJ_COUNT(self, yz, where):
  273. count = 0;
  274. with arcpy.da.SearchCursor(self.yztjjl, ["NEAR_DIST"], where) as cursor:
  275. for row in cursor:
  276. count = count + 1
  277. return str(count)
  278. def yzjg_TJ_DIST(self, yz, where):
  279. dist = 0;
  280. with arcpy.da.SearchCursor(self.yztjjl, ["NEAR_DIST"], where,
  281. sql_clause=(None, 'ORDER BY NEAR_DIST')) as cursor:
  282. for row in cursor:
  283. dist = row[0]
  284. break
  285. return str(round(dist))
  286. def yzjg_TJ_YZ(self, yz, where, key):
  287. val = "";
  288. key = key.replace("YZ.", "")
  289. with arcpy.da.SearchCursor(self.yztjjl, [key], where, sql_clause=(None, 'ORDER BY NEAR_DIST')) as cursor:
  290. for row in cursor:
  291. val = row[0]
  292. break
  293. return val
  294. def yzjg_TJ_YZS(self, yz, where, key):
  295. val = "";
  296. key = key.replace("YZ.", "").replace("[", "").replace("]", "")
  297. with arcpy.da.SearchCursor(self.yztjjl, [key], where, sql_clause=(None, 'ORDER BY NEAR_DIST')) as cursor:
  298. for row in cursor:
  299. val = val + row[0] + "、"
  300. return val[:-1]
  301. def jgrk(self, bsm, yz, jg):
  302. sql = "INSERT INTO T_FZSS_FZXZ_JGYZ(BSM,JBBSM,YZBSM,YXYZMC,YZTJ,YXZ,FXJG) VALUES ('{0}','{1}','{2}','{3}','{4}','{5}','{6}')";
  303. sql = sql.format(
  304. ''.join(str(uuid.uuid1()).split('-'))
  305. , bsm
  306. , yz['BSM']
  307. , yz['YXYZMC']
  308. , yz['YZTJ']
  309. , yz['YXZ'] if yz['YXZ'] != None else ''
  310. , jg
  311. )
  312. self.db.insert(sql)
  313. def fxlog(self, bsm, rzlx, msg):
  314. sql = "INSERT INTO T_FZSS_FXRWRZ(RWLX,RWBSM,RZLX,FXJG,RZSJ,RZLR,BSM) VALUES ('{0}','{1}','{2}','{3}',to_date('{4}','yyyy-mm-dd hh24:mi:ss'),'{5}','{6}')";
  315. sql = sql.format(
  316. '辅助选址'
  317. , bsm
  318. , rzlx
  319. , ''
  320. , utils.getNowTimeStr("%Y-%m-%d %H:%M:%S")
  321. , msg
  322. , ''.join(str(uuid.uuid1()).split('-'))
  323. )
  324. self.db.insert(sql)