C#WINFORM如何获取局域网的所有机器的IP和机器名?

止戈而立 2005-11-17 10:06:21
C#WINFORM如何获取局域网的所有机器的IP和机器名?
另外,怎样通过IP(或其它更好的方法)向这些机器发送消息?

提供思路、说明关键方法的会给高分。。。
...全文
1629 25 打赏 收藏 转发到动态 举报
写回复
用AI写文章
25 条回复
切换为时间正序
请发表友善的回复…
发表回复
LGame 2005-11-18
  • 打赏
  • 举报
回复
学习了
止戈而立 2005-11-18
  • 打赏
  • 举报
回复
好。。

各有各招。。
不错。。
overdream 2005-11-18
  • 打赏
  • 举报
回复
还有个好办法,就是用命令符net view得到所有的计算机名后放到一个.txt文本文件中,再把里面的记录一条条地读出来.
以下是核心代码:
用C#来读取文本文件:
private void button1_Click(object sender, System.EventArgs e)
{
this.openFileDialog1=new OpenFileDialog();
if(this.openFileDialog1.ShowDialog()==DialogResult.OK )
{
str_text=this.openFileDialog1.FileName;
StreamReader objReader = new StreamReader(str_text);
string sLine="";
ArrayList arrText = new ArrayList();
while (sLine != null)
{
sLine = objReader.ReadLine();
if(sLine !=null)
{

if (sLine.IndexOf("\\")==0) \\这句的功能是读取文本文件里所有含有”\\”前缀的记录
{
arrText.Add(sLine);
}
}
}
objReader.Close();
foreach (string str_out in arrText)//遍历这个数组
this.listBox1.Items.Add(str_out);
}
}
在C#中运行CMD程序或其它程序返回值:
private void button3_Click(object sender, System.EventArgs e)
{
System.Diagnostics.ProcessStartInfo psi = new System.Diagnostics.ProcessStartInfo(); psi.FileName = @"C:\WINDOWS\system32\cmd.exe ";
psi.Arguments =@"/c net view > c:\\qw.txt"; //关键是这个地方,需要加上 /c 这个参数
psi.WindowStyle=System.Diagnostics.ProcessWindowStyle.Hidden;
System.Diagnostics.Process.Start(psi);
}


PS:用完后记得再删掉这个临时的.txt文件.
overdream 2005-11-18
  • 打赏
  • 举报
回复
我这里也有个例子,前些日子作了个类似的功能,不过也要提供domainname
关于C#对于AD的操作,从AD里取得计算机名或其它AD物件.
引用
using System.DirectoryServices;
然后写
  DirectoryEntry entry = new DirectoryEntry("LDAP://NobleLighting");
DirectorySearcher mySearcher = new DirectorySearcher(entry);
mySearcher.Filter = ("(objectCategory=computer)");
foreach(SearchResult resEnt in mySearcher.FindAll())
{

this.listBox1.Items.Add(resEnt.GetDirectoryEntry().Name.ToString().Remove(0,3));
}
//关于objectclass的一点补充
//在DirectorySearcher的Filler有以下object
//(&(objectCategory=computer)(location=Building 7N))
//(&(objectClass=user)(objectCategory=person))
//(&(objectClass=contact)(objectCategory=person))
//(objectCategory=person)
//objectClass=organizationalUnit 查询条件是所有的组织单元(OU)
// 2. objectClass=group 查询条件是所有的组(GROUP)
// 3. objectClass=user 查询条件是所有的用户(USER)
//DirectorySearcher类的Findall方法用来递归的查找所有符合条件的对象。其返回结果
// 是一个SearchResult类型的对象,这是一个集合类型。
// ü 用Foreach语句访问集合中的所有对象,获得对象的信息。
这样就把AD里的计算机名称都加入到ListBox里了.
ccj820910 2005-11-18
  • 打赏
  • 举报
回复
mark
止戈而立 2005-11-18
  • 打赏
  • 举报
回复
再顶顶。。
止戈而立 2005-11-18
  • 打赏
  • 举报
回复
好。。准备散分了。。
BigIdiot628 2005-11-17
  • 打赏
  • 举报
回复
public delegate void UpdateList ( string sIP , string sHostName ) ;
public class ping
{
public UpdateList ul ;
public string ip ; //接收传送来的IP地址字符串
public string HostName ;//向主进展传递对应IP地址是否在线数据
//这个过程用来判断传送来的IP地址对应计算机是否在线
public void scan ( )
{
IPAddress myIP = IPAddress.Parse ( ip ) ;
try
{
IPHostEntry myHost = Dns.GetHostByAddress ( myIP );
HostName = myHost.HostName.ToString ( ) ;
}
catch
{
HostName = "" ;
}
if (HostName == "")
HostName = " 主机没有响应!";
if ( ul != null)
ul ( ip , HostName ) ;
}
}

void UpdateMyList ( string sIP , string sHostName )
{
lock ( listBox1 )
{
listBox1.Items.Add ( sIP + " " + sHostName ) ;
if ( progressBar1.Value != progressBar1.Maximum )
{
progressBar1.Value++ ;
}
if ( progressBar1.Value == progressBar1.Maximum )
{
MessageBox.Show ( "成功完成检测!" , "提示" ) ;
DateTime EndTime = DateTime.Now ;
TimeSpan ts = EndTime - StartTime ;
label4.Text = ts.Seconds.ToString ( ) + "秒" ;
progressBar1.Value = progressBar1.Minimum ;
}
}
}
BigIdiot628 2005-11-17
  • 打赏
  • 举报
回复
using System.Net.Sockets ;
using System.Net ;

int i ;
for ( i = Min ; i <= Max ; i++ )
{
string ip= mask + i.ToString ( ) ;
IPAddress myIP = IPAddress.Parse ( ip ) ;
//根据给定的IP地址字符串,处境IPAddress实例
try
{
IPHostEntry myHost = Dns.GetHostByAddress ( myIP ) ;
string HostName = myHost.HostName.ToString ( ) ;
listBox1.Items.Add ( ip + "名称为:" + HostName ) ;
}
catch
{
listBox1.Items.Add ( ip + "主机没有响应!" ) ;
}
}
暗石绿 2005-11-17
  • 打赏
  • 举报
回复
Mark
止戈而立 2005-11-17
  • 打赏
  • 举报
回复
看来还是挺多人想写这方面的程序的嘛。。。
hs117 2005-11-17
  • 打赏
  • 举报
回复
我做了个局域网聊天软件
不知道怎么向别的机子发送信息
怎么实现?
请高手说一下,谢谢!
止戈而立 2005-11-17
  • 打赏
  • 举报
回复
谢谢楼上的朋友。。

楼下的朋友可以说说第二个问题。。或者第一个问题的其它实现方法。。

我明天回来结帖。。
NaZiChong 2005-11-17
  • 打赏
  • 举报
回复
//写这个程序,为了是显示局域网内的主机,然后通过用户点击选中的机器,检查是否该主机上安装有SQLSERVER,是为一个配置程序所写的
//这里提供CODE,给有需要的朋友

//设置DLL必须使用该命名空间
using System.Runtime.InteropServices;

#region 动态链接库定义
[DllImport("mpr.dll",CharSet=CharSet.Auto)] private static extern int WNetEnumResource(IntPtr hEnum, ref int lpcCount,IntPtr lpBuffer, ref int lpBufferSize );
[DllImport("mpr.dll",CharSet=CharSet.Auto)] private static extern int WNetOpenEnum(RESOURCE_SCOPE dwScope,RESOURCE_TYPE dwType,RESOURCE_USAGE dwUsage,[MarshalAs(UnmanagedType.AsAny)][In] Object lpNetResource,out IntPtr lphEnum);
[DllImport("mpr.dll",CharSet=CharSet.Auto)] private static extern int WNetCloseEnum( IntPtr hEnum );
#endregion

#region 定义枚举常量
public enum RESOURCE_SCOPE
{
RESOURCE_CONNECTED = 0x00000001,
RESOURCE_GLOBALNET = 0x00000002,
RESOURCE_REMEMBERED = 0x00000003,
RESOURCE_RECENT= 0x00000004,
RESOURCE_CONTEXT= 0x00000005
}

public enum RESOURCE_TYPE
{
RESOURCETYPE_ANY= 0x00000000,
RESOURCETYPE_DISK= 0x00000001,
RESOURCETYPE_PRINT = 0x00000002,
RESOURCETYPE_RESERVED = 0x00000008,
}

public enum RESOURCE_USAGE
{
RESOURCEUSAGE_CONNECTABLE =0x00000001,
RESOURCEUSAGE_CONTAINER=0x00000002,
RESOURCEUSAGE_NOLOCALDEVICE =0x00000004,
RESOURCEUSAGE_SIBLING=0x00000008,
RESOURCEUSAGE_ATTACHED=0x00000010,
RESOURCEUSAGE_ALL =(RESOURCEUSAGE_CONNECTABLE | RESOURCEUSAGE_CONTAINER | RESOURCEUSAGE_ATTACHED),
}

public enum RESOURCE_DISPLAYTYPE
{
RESOURCEDISPLAYTYPE_GENERIC= 0x00000000,
RESOURCEDISPLAYTYPE_DOMAIN= 0x00000001,
RESOURCEDISPLAYTYPE_SERVER= 0x00000002,

RESOURCEDISPLAYTYPE_SHARE= 0x00000003,
RESOURCEDISPLAYTYPE_FILE = 0x00000004,
RESOURCEDISPLAYTYPE_GROUP= 0x00000005,
RESOURCEDISPLAYTYPE_NETWORK= 0x00000006,
RESOURCEDISPLAYTYPE_ROOT = 0x00000007,
RESOURCEDISPLAYTYPE_SHAREADMIN = 0x00000008,
RESOURCEDISPLAYTYPE_DIRECTORY = 0x00000009,
RESOURCEDISPLAYTYPE_TREE = 0x0000000A,
RESOURCEDISPLAYTYPE_NDSCONTAINER = 0x0000000B
}

public struct NETRESOURCE
{
public RESOURCE_SCOPE dwScope;
public RESOURCE_TYPE dwType;
public RESOURCE_DISPLAYTYPE dwDisplayType;
public RESOURCE_USAGE dwUsage;
[MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPTStr)] public string lpLocalName;
[MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPTStr)] public string lpRemoteName;
[MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPTStr)] public string lpComment;
[MarshalAs(System.Runtime.InteropServices.UnmanagedType.LPTStr)] public string lpProvider;
}

public enum NERR
{
NERR_Success = 0,/* Success */
ERROR_MORE_DATA = 234, // dderror
ERROR_NO_BROWSER_SERVERS_FOUND = 6118,
ERROR_INVALID_LEVEL = 124,
ERROR_ACCESS_DENIED = 5,
ERROR_INVALID_PARAMETER = 87,
ERROR_NOT_ENOUGH_MEMORY = 8,
ERROR_NETWORK_BUSY = 54,
ERROR_BAD_NETPATH = 53,
ERROR_NO_NETWORK = 1222,
ERROR_INVALID_HANDLE_STATE = 1609,
ERROR_EXTENDED_ERROR= 1208
}
#endregion


#region 开始列举网络函数
public TreeNode pNode1;
public TreeNode pNode2;
public TreeNode pNode3;
private void WNETOE(Object o)
{
int iRet;
IntPtr ptrHandle = new IntPtr();
try
{
iRet =WNetOpenEnum(RESOURCE_SCOPE.RESOURCE_GLOBALNET,RESOURCE_TYPE.RESOURCETYPE_ANY,RESOURCE_USAGE.RESOURCEUSAGE_ALL,o,out ptrHandle );
if( iRet != 0 )return;

int entries;
int buffer = 16384;
IntPtr ptrBuffer = Marshal.AllocHGlobal(buffer);
NETRESOURCE nr;

for(;;)
{
entries = -1;
buffer = 16384;
iRet =WNetEnumResource(ptrHandle,ref entries,ptrBuffer,ref buffer);
if((iRet != 0) || (entries<1))break;

Int32 ptr = ptrBuffer.ToInt32();
for(int i=0;i<entries;i++ )
{
nr = (NETRESOURCE)Marshal.PtrToStructure( new IntPtr(ptr), typeof(NETRESOURCE) );
if(RESOURCE_USAGE.RESOURCEUSAGE_CONTAINER == (nr.dwUsage & RESOURCE_USAGE.RESOURCEUSAGE_CONTAINER))
{

ptr += Marshal.SizeOf( nr );
if(nr.dwDisplayType == RESOURCE_DISPLAYTYPE.RESOURCEDISPLAYTYPE_NETWORK)
{
pNode1 = tView.Nodes.Add(nr.lpRemoteName);//TreeView
pNode1.ImageIndex = 0;
pNode1.SelectedImageIndex = 0;
}
else if(nr.dwDisplayType == RESOURCE_DISPLAYTYPE.RESOURCEDISPLAYTYPE_DOMAIN)
{
pNode2 = pNode1.Nodes.Add(nr.lpRemoteName);
pNode2.ImageIndex = 1;
pNode2.SelectedImageIndex =1;
}
else if(nr.dwDisplayType == RESOURCE_DISPLAYTYPE.RESOURCEDISPLAYTYPE_SERVER)
{
string sPCName = nr.lpRemoteName;
pNode3 = pNode2.Nodes.Add(sPCName.Substring(2,sPCName.Length-2));\\此处为去处机器名称前的两个"\\"字符
pNode3.ImageIndex = 2;
pNode3.SelectedImageIndex = 2;
}

WNETOE(nr);
}

}
}
Marshal.FreeHGlobal( ptrBuffer );
iRet =WNetCloseEnum( ptrHandle );
}
catch(Exception ex)
{
MessageBox.Show("查找本地网络错误:"+ex.Message,"错误",MessageBoxButtons.OK,MessageBoxIcon.Error);
}
}

#endregion

//窗体LOAD事件中,使用函数
private void frmDBConnConfig_Load(object sender, System.EventArgs e)
{
WNETOE(null);
}
NaZiChong 2005-11-17
  • 打赏
  • 举报
回复
DirectoryEntry root = new DirectoryEntry("WinNT:");

foreach(DirectoryEntry domain in root.Children)
{
lb_pcName.Text ="";
lb_pcName.Items.Add("工作组:"+domain.Name+"");
foreach(DirectoryEntry pc in domain.Children)
{
if(pc.Name!="Schema")//Schema是结束标记
lb_pcName.Items.Add("机器名:"+pc.Name+"");
}
}
止戈而立 2005-11-17
  • 打赏
  • 举报
回复
谢谢各位帮顶。。

cjzlxy(享受孤独)的思路不错。。
看看其他高手怎么实现???
cjzlxy 2005-11-17
  • 打赏
  • 举报
回复
只能给你说一下思路,因为我也不太懂..
先获取自己机器IP.这个很容易
然后解析IP段,遍历,发送数据探测.
列出局域网所有在线机器IP
然后根据IP获取机器名
lampson123 2005-11-17
  • 打赏
  • 举报
回复
也想知道,帮顶起来
asuan 2005-11-17
  • 打赏
  • 举报
回复
mark
jxzhang615 2005-11-17
  • 打赏
  • 举报
回复
帮你顶先
加载更多回复(5)

110,535

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术 C#
社区管理员
  • C#
  • Web++
  • by_封爱
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

让您成为最强悍的C#开发者

试试用AI创作助手写篇文章吧