You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用python-snap7连接西门子1500 PLC读写数据时遇TypeError求助

问题

使用Python的snap7库连接西门子CPU 1500 PLC,连接成功,但读写内存时出现如下错误:

readbit = ReadMemory(plc, 0, 0, S7WLBit) #read m0.0

  File c:\users\rachid\.spyder-py3\sps.py:22 in ReadMemory
    result = plc.read_area(areas['MK'],0,byte,datatype)

  File ~\anaconda3\Lib\site-packages\snap7\client\__init__.py:390 in read_area
    if area not in Areas:

  File ~\anaconda3\Lib\enum.py:740 in __contains__
    raise TypeError(

TypeError: unsupported operand type(s) for 'in': 'int' and 'EnumType'

原代码如下:

import snap7
from snap7.util import*
from snap7.types import*
import time


def ReadMemory(plc,byte,bit,datatype):
    result = plc.read_area(areas['MK'],0,byte,datatype)
    if datatype==S7WLBit:
        return get_bool(result,0,1)
    elif datatype==S7WLByte or datatype==S7WLWord:
        return get_int(result,0)
    elif datatype==S7WLReal:
        return get_real(result,0)
    elif datatype==S7WLDWord:
        return get_dword(result,0)
    else:
        return None
    

def WriteMemory(plc,byte,bit,datatype,value):
    result = plc.read_area(areas['MK'],0,byte,datatype)
    if datatype==S7WLBit:
        set_bool(result,0,bit,value)
    elif datatype==S7WLByte or datatype==S7WLWord:
        set_int(result,0,value)
    elif datatype==S7WLReal:
        set_real(result,0,value)
    elif datatype==S7WLDWord:
        set_dword(result,0,value)
    plc.write_area(areas['MK'],0,byte,result)       


# Verbindung zur SPS herstellen
plc = snap7.client.Client()
plc.connect(spshost, 0, 1)     #IP, RACK , SLOT 

state = plc.get_cpu_state()
print(f'State:{state}')

a = 0
b = 0
c = 0
while True:
    readbit = ReadMemory(plc, 0, 0, S7WLBit) #read m0.0
    print('readbit: ', readbit)
    readword = ReadMemory(plc, 10, 0, S7WLWord) #read mw10
    print('readbyte: ',readword)
    readreal = ReadMemory(plc, 15, 0, S7WLReal) #read md15
    print('readreal: ',readreal)
    readDword = ReadMemory(plc, 20, 0, S7WLDWord) #read md20
    print('readDword: ', readDword)
    
    a = a+1
    b = b+2.4
    c = c+10
    #write memory
    WriteMemory(plc, 0, 3, S7WLBit, True) #write m0.3 True
    time.sleep(1)
    WriteMemory(plc, 0, 3, S7WLBit, False) #write m0.3 False
    time.sleep(1)
    WriteMemory(plc, 30, 0, S7WLWord, a) #write mw30 valuefrom a variable
    WriteMemory(plc, 40, 0, S7WLReal, b) #write md40 value
    WriteMemory(plc, 50, 0, S7WLDWord, c) #write md50 value
修复方案

错误根源是snap7新版本中Areas为枚举类型,不再兼容旧版本的整数传参方式,结合代码其他问题,修复点如下:

  • 替换内存区域参数:用snap7.types.Areas枚举值替代旧的areas['MK']写法,比如Areas.MK
  • 修正位读取索引:原代码中读取位时固定用get_bool(result,0,1),改为使用传入的bit参数,确保读取指定位
  • 补充PLC地址定义:原代码中spshost未定义,需添加实际PLC的IP地址

修改后的完整代码:

import snap7
from snap7.util import *
from snap7.types import *
import time

def ReadMemory(plc, byte, bit, datatype):
    # 使用Areas枚举替代旧字典写法
    result = plc.read_area(Areas.MK, 0, byte, datatype)
    if datatype == S7WLBit:
        # 修复位索引,使用传入的bit参数
        return get_bool(result, 0, bit)
    elif datatype == S7WLByte or datatype == S7WLWord:
        return get_int(result, 0)
    elif datatype == S7WLReal:
        return get_real(result, 0)
    elif datatype == S7WLDWord:
        return get_dword(result, 0)
    else:
        return None

def WriteMemory(plc, byte, bit, datatype, value):
    # 使用Areas枚举替代旧字典写法
    result = plc.read_area(Areas.MK, 0, byte, datatype)
    if datatype == S7WLBit:
        set_bool(result, 0, bit, value)
    elif datatype == S7WLByte or datatype == S7WLWord:
        set_int(result, 0, value)
    elif datatype == S7WLReal:
        set_real(result, 0, value)
    elif datatype == S7WLDWord:
        set_dword(result, 0, value)
    plc.write_area(Areas.MK, 0, byte, result)

# 定义PLC实际IP地址
spshost = "192.168.0.1"  # 替换为你的PLC IP
plc = snap7.client.Client()
plc.connect(spshost, 0, 1)     # IP, RACK , SLOT 

state = plc.get_cpu_state()
print(f'State:{state}')

a = 0
b = 0.0
c = 0
while True:
    readbit = ReadMemory(plc, 0, 0, S7WLBit) # read m0.0
    print('readbit: ', readbit)
    readword = ReadMemory(plc, 10, 0, S7WLWord) # read mw10
    print('readword: ', readword)
    readreal = ReadMemory(plc, 15, 0, S7WLReal) # read md15
    print('readreal: ', readreal)
    readDword = ReadMemory(plc, 20, 0, S7WLDWord) # read md20
    print('readDword: ', readDword)
    
    a += 1
    b += 2.4
    c += 10
    # write memory
    WriteMemory(plc, 0, 3, S7WLBit, True) # write m0.3 True
    time.sleep(1)
    WriteMemory(plc, 0, 3, S7WLBit, False) # write m0.3 False
    time.sleep(1)
    WriteMemory(plc, 30, 0, S7WLWord, a) # write mw30 value from variable
    WriteMemory(plc, 40, 0, S7WLReal, b) # write md40 value
    WriteMemory(plc, 50, 0, S7WLDWord, c) # write md50 value

内容的提问来源于stack exchange,提问作者mzr97

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.01 01:35:25