haskell
haskell批量修改文件名
六 19th
import System.Directory
import System (getArgs)
import Text.Regex.Posix
zipOldNewNames :: String -> String -> [String] -> [(String,String)]
– matchFile :: String -> Bool
– oldNewPair :: String -> (String,String)
– getPostfixName :: String -> String
zipOldNewNames filePat newNamePrefix names = catMaybes $ map zipOldNewName names
where zipOldNewName name = if matchFile name then Just (oldNewPair name) else Nothing
matchFile name = name =~ filePat
oldNewPair name = let p = getPostfixName name in (name,newNamePrefix ++ p :: String)
getPostfixName name = let (a,b,c,d) = name =~ filePat :: (String,String,String,[String]) in head d
showTable xs = concatMap format xs
where
format (a, b) = a ++ " : " ++ b ++ "\n"
main = do
args <- getArgs
let filePat = args !! 0 – 正则表达式,\1为保留的后缀
let dirName = args !! 1 – 目录,需要保留最后的"\"(win)或”/”(linux)
let newNamePrefix = args !! 2 – 文件名新前缀
names <- getDirectoryContents dirName
let names_ent = filter (`notElem` [".",".."]) names
let oldNewNames = zipOldNewNames filePat newNamePrefix names_ent
putStr $ showTable oldNewNames – 打印旧:新文件名的对比
mapM_ (\(x,y) -> renameFile (dirName ++ x) (dirName ++ y)) oldNewNames – 更改文件名
putStrLn "finishes!"
[翻译]Infinity in Haskell
五 23rd
在众多编程语言中,Haskell如此有趣,是因为它的异类特性和支持者传教般的热情。像下面的一个例子就最好的解释了为什么出现这种情况。这四行代码是对the Sieve of Eratosthenes,一个素数列表的经典算法的实现(G. Hutton, Programming in Haskell. Cambridge: Cambridge University Press, 2007):
> primes :: [Int]
> primes = sieve [2..]
> sieve :: [Int] => [Int]
> sieve (p : xs) = p : sieve [x | x <= xs, x `mod` p ≠ 0]
在这里发生的事情是函数sieve使用了无限的列表
[2..] = [2, 3, 4, 5, 6, 7,...]。
函数sieve使用一个整数列表作为参数,并返回一个整数列表;它接受参数列表的第一个数字p为素数,然后递归调用自身,新的参数是从原来列表中过滤掉p的所有倍数所获得的列表。在Haskell中,表达式通过按名调用(call-by-name)求值来执行,而不是按值调用(call-by-value)求值。这就像在数学计算中操纵符号或公式,在最后一步才替换在表达式中的数值。这种求值的方法导致函数primes返回一个(潜在无限的,如果硬件局限和太阳系期望寿命许可)包含无限数字的列表。
对于一个数学家,上面四行haskell代码是一个启示。
首先,该程序(和计算机运行此程序)似乎成功地操纵无限集合。其次,适度的四行代码根本不理百年来关于实际的和潜在的无限的争议,将似乎不可调和的概念一起融入了“内部集合理论”的精神(E. Nelson, Internal set theory, a new approach to NSA, Bulletin of the American Mathematical Society, 83 (1977), 1165-1198; A. M. Robert, Nonstandard Analysis. Mineola, NY: Dover Publications, 2003.):一个无限集合被视为一个真正的对象,因为它被赋予一个名字,然后被当作是一个实际对象的名称。另一方面,我们只能使用集合中那些我们已经明确地构造的元素。这个集合就像一个饼干罐,里面只包含那些我们已经放进去的饼干,但我们可以将这个罐子从一个架子上拿出来,放到桌子上,而不管它包含多少饼干。
[原文] http://micromath.wordpress.com/2011/05/12/infinity-in-haskell/
游戏辅助作弊工具
二 7th
最近在玩北欧女神,陷入苦战,眼看假期就要结束,还没通关,又没有作弊器,只能手动编辑存档文件,修改属性。为便于查找地址,写了个辅助工具(只对属性地址不变的存档有效)。
使用方法:findBinaryFile [存档文件] [数值]
如果输出多个地址,就进行下游戏再存档,然后查找新数值的地址。
==== findBinaryFile.hs =====
import Numeric
import Data.List
import System.IO
import System.Environment
import qualified Data.ByteString as B
transHex :: String -> [String]
transHex = reverse . foldr transHex' [[]]
transHex' x z@(y:ys) =
if length y == 2 then
[x] : z
else ((x:y):ys)
transHex' x [] = [[x]]
hex2Num = fst . (!! 0) . readHex
main = do
args <- getArgs
let rFileName = args !! 0
let rawNum = read $ args !! 1
let findMe = B.pack $ map hex2Num $ transHex $ showHex rawNum ""
handle <- openBinaryFile rFileName ReadMode
content <- B.hGetContents handle
let posList = B.findSubstrings findMe content
hClose handle
mapM_ putStrLn $ map (flip showHex "") posList
haskell版explode
八 24th